axol_http/header/names.rs
1use std::{
2 collections::HashSet,
3 hash::{Hash, Hasher},
4};
5
6/// A string that will match others regardless of ascii case
7#[derive(Clone, Copy, Debug)]
8struct CaselessStr<'a>(&'a str);
9
10impl<'a, 'b> PartialEq<CaselessStr<'b>> for CaselessStr<'a> {
11 fn eq(&self, other: &CaselessStr<'b>) -> bool {
12 self.0.eq_ignore_ascii_case(other.0)
13 }
14}
15
16impl<'a, 'b> Eq for CaselessStr<'a> {}
17
18impl Hash for CaselessStr<'_> {
19 fn hash<H: Hasher>(&self, state: &mut H) {
20 let mut start = 0usize;
21 let bytes = self.0.as_bytes();
22 for i in 0..bytes.len() {
23 if bytes[i] >= b'A' && bytes[i] <= b'Z' {
24 if start != i {
25 state.write(&bytes[start..i]);
26 }
27 start = i + 1;
28 state.write(&[bytes[i] + b' ']);
29 }
30 }
31 if start != bytes.len() {
32 state.write(&bytes[start..]);
33 }
34 state.write(&[0xff]);
35 }
36}
37
38macro_rules! standard_headers {
39 (
40 $(
41 $(#[$docs:meta])*
42 ($konst:ident, $upcase:ident, $name_bytes:literal);
43 )+
44 ) => {
45 $(
46 $(#[$docs])*
47 pub const $upcase: &'static str = $name_bytes;
48 )+
49 const ALL_HEADERS: &[&'static str] = &[
50 $(
51 $upcase,
52 )+
53 ];
54 }
55}
56
57lazy_static::lazy_static! {
58 static ref HEADER_MAP: HashSet<CaselessStr<'static>> = {
59 let mut out = HashSet::new();
60 for header in ALL_HEADERS {
61 out.insert(CaselessStr(*header));
62 }
63 out
64 };
65}
66
67/// If found, returns a static reference to an ascii lowercase version of `name`.
68pub(super) fn maybe_static_lowercase<'a>(name: &'a str) -> Option<&'static str> {
69 let value: Option<&CaselessStr<'a>> = HEADER_MAP.get(&CaselessStr(name));
70 match value {
71 Some(x) => {
72 let x: &'a str = (*x).0;
73 // SAFETY: this is safe because the underlying value in the hashset is 'static, but weird type coercion
74 // and inability to implement borrow (cannot state 'a: ! 'static) yields to this
75 let x: &'static str = unsafe { std::mem::transmute(x) };
76 Some(x)
77 }
78 None => None,
79 }
80}
81
82// Generate constants for all standard HTTP headers. This includes a static hash
83// code for the "fast hash" path. The hash code for static headers *do not* have
84// to match the text representation of those headers. This is because header
85// strings are always converted to the static values (when they match) before
86// being hashed. This means that it is impossible to compare the static hash
87// code of CONTENT_LENGTH with "content-length".
88standard_headers! {
89 /// Advertises which content types the client is able to understand.
90 ///
91 /// The Accept request HTTP header advertises which content types, expressed
92 /// as MIME types, the client is able to understand. Using content
93 /// negotiation, the server then selects one of the proposals, uses it and
94 /// informs the client of its choice with the Content-Type response header.
95 /// Browsers set adequate values for this header depending of the context
96 /// where the request is done: when fetching a CSS stylesheet a different
97 /// value is set for the request than when fetching an image, video or a
98 /// script.
99 (Accept, ACCEPT, "accept");
100
101 /// Advertises which character set the client is able to understand.
102 ///
103 /// The Accept-Charset request HTTP header advertises which character set
104 /// the client is able to understand. Using content negotiation, the server
105 /// then selects one of the proposals, uses it and informs the client of its
106 /// choice within the Content-Type response header. Browsers usually don't
107 /// set this header as the default value for each content type is usually
108 /// correct and transmitting it would allow easier fingerprinting.
109 ///
110 /// If the server cannot serve any matching character set, it can
111 /// theoretically send back a 406 (Not Acceptable) error code. But, for a
112 /// better user experience, this is rarely done and the more common way is
113 /// to ignore the Accept-Charset header in this case.
114 (AcceptCharset, ACCEPT_CHARSET, "accept-charset");
115
116 /// Advertises which content encoding the client is able to understand.
117 ///
118 /// The Accept-Encoding request HTTP header advertises which content
119 /// encoding, usually a compression algorithm, the client is able to
120 /// understand. Using content negotiation, the server selects one of the
121 /// proposals, uses it and informs the client of its choice with the
122 /// Content-Encoding response header.
123 ///
124 /// Even if both the client and the server supports the same compression
125 /// algorithms, the server may choose not to compress the body of a
126 /// response, if the identity value is also acceptable. Two common cases
127 /// lead to this:
128 ///
129 /// * The data to be sent is already compressed and a second compression
130 /// won't lead to smaller data to be transmitted. This may the case with
131 /// some image formats;
132 ///
133 /// * The server is overloaded and cannot afford the computational overhead
134 /// induced by the compression requirement. Typically, Microsoft recommends
135 /// not to compress if a server use more than 80 % of its computational
136 /// power.
137 ///
138 /// As long as the identity value, meaning no encryption, is not explicitly
139 /// forbidden, by an identity;q=0 or a *;q=0 without another explicitly set
140 /// value for identity, the server must never send back a 406 Not Acceptable
141 /// error.
142 (AcceptEncoding, ACCEPT_ENCODING, "accept-encoding");
143
144 /// Advertises which languages the client is able to understand.
145 ///
146 /// The Accept-Language request HTTP header advertises which languages the
147 /// client is able to understand, and which locale variant is preferred.
148 /// Using content negotiation, the server then selects one of the proposals,
149 /// uses it and informs the client of its choice with the Content-Language
150 /// response header. Browsers set adequate values for this header according
151 /// their user interface language and even if a user can change it, this
152 /// happens rarely (and is frown upon as it leads to fingerprinting).
153 ///
154 /// This header is a hint to be used when the server has no way of
155 /// determining the language via another way, like a specific URL, that is
156 /// controlled by an explicit user decision. It is recommended that the
157 /// server never overrides an explicit decision. The content of the
158 /// Accept-Language is often out of the control of the user (like when
159 /// traveling and using an Internet Cafe in a different country); the user
160 /// may also want to visit a page in another language than the locale of
161 /// their user interface.
162 ///
163 /// If the server cannot serve any matching language, it can theoretically
164 /// send back a 406 (Not Acceptable) error code. But, for a better user
165 /// experience, this is rarely done and more common way is to ignore the
166 /// Accept-Language header in this case.
167 (AcceptLanguage, ACCEPT_LANGUAGE, "accept-language");
168
169 /// Marker used by the server to advertise partial request support.
170 ///
171 /// The Accept-Ranges response HTTP header is a marker used by the server to
172 /// advertise its support of partial requests. The value of this field
173 /// indicates the unit that can be used to define a range.
174 ///
175 /// In presence of an Accept-Ranges header, the browser may try to resume an
176 /// interrupted download, rather than to start it from the start again.
177 (AcceptRanges, ACCEPT_RANGES, "accept-ranges");
178
179 /// Preflight response indicating if the response to the request can be
180 /// exposed to the page.
181 ///
182 /// The Access-Control-Allow-Credentials response header indicates whether
183 /// or not the response to the request can be exposed to the page. It can be
184 /// exposed when the true value is returned; it can't in other cases.
185 ///
186 /// Credentials are cookies, authorization headers or TLS client
187 /// certificates.
188 ///
189 /// When used as part of a response to a preflight request, this indicates
190 /// whether or not the actual request can be made using credentials. Note
191 /// that simple GET requests are not preflighted, and so if a request is
192 /// made for a resource with credentials, if this header is not returned
193 /// with the resource, the response is ignored by the browser and not
194 /// returned to web content.
195 ///
196 /// The Access-Control-Allow-Credentials header works in conjunction with
197 /// the XMLHttpRequest.withCredentials property or with the credentials
198 /// option in the Request() constructor of the Fetch API. Credentials must
199 /// be set on both sides (the Access-Control-Allow-Credentials header and in
200 /// the XHR or Fetch request) in order for the CORS request with credentials
201 /// to succeed.
202 (AccessControlAllowCredentials, ACCESS_CONTROL_ALLOW_CREDENTIALS, "access-control-allow-credentials");
203
204 /// Preflight response indicating permitted HTTP headers.
205 ///
206 /// The Access-Control-Allow-Headers response header is used in response to
207 /// a preflight request to indicate which HTTP headers will be available via
208 /// Access-Control-Expose-Headers when making the actual request.
209 ///
210 /// The simple headers, Accept, Accept-Language, Content-Language,
211 /// Content-Type (but only with a MIME type of its parsed value (ignoring
212 /// parameters) of either application/x-www-form-urlencoded,
213 /// multipart/form-data, or text/plain), are always available and don't need
214 /// to be listed by this header.
215 ///
216 /// This header is required if the request has an
217 /// Access-Control-Request-Headers header.
218 (AccessControlAllowHeaders, ACCESS_CONTROL_ALLOW_HEADERS, "access-control-allow-headers");
219
220 /// Preflight header response indicating permitted access methods.
221 ///
222 /// The Access-Control-Allow-Methods response header specifies the method or
223 /// methods allowed when accessing the resource in response to a preflight
224 /// request.
225 (AccessControlAllowMethods, ACCESS_CONTROL_ALLOW_METHODS, "access-control-allow-methods");
226
227 /// Indicates whether the response can be shared with resources with the
228 /// given origin.
229 (AccessControlAllowOrigin, ACCESS_CONTROL_ALLOW_ORIGIN, "access-control-allow-origin");
230
231 /// Indicates which headers can be exposed as part of the response by
232 /// listing their names.
233 (AccessControlExposeHeaders, ACCESS_CONTROL_EXPOSE_HEADERS, "access-control-expose-headers");
234
235 /// Indicates how long the results of a preflight request can be cached.
236 (AccessControlMaxAge, ACCESS_CONTROL_MAX_AGE, "access-control-max-age");
237
238 /// Informs the server which HTTP headers will be used when an actual
239 /// request is made.
240 (AccessControlRequestHeaders, ACCESS_CONTROL_REQUEST_HEADERS, "access-control-request-headers");
241
242 /// Informs the server know which HTTP method will be used when the actual
243 /// request is made.
244 (AccessControlRequestMethod, ACCESS_CONTROL_REQUEST_METHOD, "access-control-request-method");
245
246 /// Indicates the time in seconds the object has been in a proxy cache.
247 ///
248 /// The Age header is usually close to zero. If it is Age: 0, it was
249 /// probably just fetched from the origin server; otherwise It is usually
250 /// calculated as a difference between the proxy's current date and the Date
251 /// general header included in the HTTP response.
252 (Age, AGE, "age");
253
254 /// Lists the set of methods support by a resource.
255 ///
256 /// This header must be sent if the server responds with a 405 Method Not
257 /// Allowed status code to indicate which request methods can be used. An
258 /// empty Allow header indicates that the resource allows no request
259 /// methods, which might occur temporarily for a given resource, for
260 /// example.
261 (Allow, ALLOW, "allow");
262
263 /// Advertises the availability of alternate services to clients.
264 (AltSvc, ALT_SVC, "alt-svc");
265
266 /// Contains the credentials to authenticate a user agent with a server.
267 ///
268 /// Usually this header is included after the server has responded with a
269 /// 401 Unauthorized status and the WWW-Authenticate header.
270 (Authorization, AUTHORIZATION, "authorization");
271
272 /// Specifies directives for caching mechanisms in both requests and
273 /// responses.
274 ///
275 /// Caching directives are unidirectional, meaning that a given directive in
276 /// a request is not implying that the same directive is to be given in the
277 /// response.
278 (CacheControl, CACHE_CONTROL, "cache-control");
279
280 /// Indicates how caches have handled a response and its corresponding request.
281 ///
282 /// See [RFC 9211](https://www.rfc-editor.org/rfc/rfc9211.html).
283 (CacheStatus, CACHE_STATUS, "cache-status");
284
285 /// Specifies directives that allow origin servers to control the behavior of CDN caches
286 /// interposed between them and clients separately from other caches that might handle the
287 /// response.
288 ///
289 /// See [RFC 9213](https://www.rfc-editor.org/rfc/rfc9213.html).
290 (CdnCacheControl, CDN_CACHE_CONTROL, "cdn-cache-control");
291
292 /// Controls whether or not the network connection stays open after the
293 /// current transaction finishes.
294 ///
295 /// If the value sent is keep-alive, the connection is persistent and not
296 /// closed, allowing for subsequent requests to the same server to be done.
297 ///
298 /// Except for the standard hop-by-hop headers (Keep-Alive,
299 /// Transfer-Encoding, TE, Connection, Trailer, Upgrade, Proxy-Authorization
300 /// and Proxy-Authenticate), any hop-by-hop headers used by the message must
301 /// be listed in the Connection header, so that the first proxy knows he has
302 /// to consume them and not to forward them further. Standard hop-by-hop
303 /// headers can be listed too (it is often the case of Keep-Alive, but this
304 /// is not mandatory.
305 (Connection, CONNECTION, "connection");
306
307 /// Indicates if the content is expected to be displayed inline.
308 ///
309 /// In a regular HTTP response, the Content-Disposition response header is a
310 /// header indicating if the content is expected to be displayed inline in
311 /// the browser, that is, as a Web page or as part of a Web page, or as an
312 /// attachment, that is downloaded and saved locally.
313 ///
314 /// In a multipart/form-data body, the HTTP Content-Disposition general
315 /// header is a header that can be used on the subpart of a multipart body
316 /// to give information about the field it applies to. The subpart is
317 /// delimited by the boundary defined in the Content-Type header. Used on
318 /// the body itself, Content-Disposition has no effect.
319 ///
320 /// The Content-Disposition header is defined in the larger context of MIME
321 /// messages for e-mail, but only a subset of the possible parameters apply
322 /// to HTTP forms and POST requests. Only the value form-data, as well as
323 /// the optional directive name and filename, can be used in the HTTP
324 /// context.
325 (ContentDisposition, CONTENT_DISPOSITION, "content-disposition");
326
327 /// Used to compress the media-type.
328 ///
329 /// When present, its value indicates what additional content encoding has
330 /// been applied to the entity-body. It lets the client know, how to decode
331 /// in order to obtain the media-type referenced by the Content-Type header.
332 ///
333 /// It is recommended to compress data as much as possible and therefore to
334 /// use this field, but some types of resources, like jpeg images, are
335 /// already compressed. Sometimes using additional compression doesn't
336 /// reduce payload size and can even make the payload longer.
337 (ContentEncoding, CONTENT_ENCODING, "content-encoding");
338
339 /// Used to describe the languages intended for the audience.
340 ///
341 /// This header allows a user to differentiate according to the users' own
342 /// preferred language. For example, if "Content-Language: de-DE" is set, it
343 /// says that the document is intended for German language speakers
344 /// (however, it doesn't indicate the document is written in German. For
345 /// example, it might be written in English as part of a language course for
346 /// German speakers).
347 ///
348 /// If no Content-Language is specified, the default is that the content is
349 /// intended for all language audiences. Multiple language tags are also
350 /// possible, as well as applying the Content-Language header to various
351 /// media types and not only to textual documents.
352 (ContentLanguage, CONTENT_LANGUAGE, "content-language");
353
354 /// Indicates the size of the entity-body.
355 ///
356 /// The header value must be a decimal indicating the number of octets sent
357 /// to the recipient.
358 (ContentLength, CONTENT_LENGTH, "content-length");
359
360 /// Indicates an alternate location for the returned data.
361 ///
362 /// The principal use case is to indicate the URL of the resource
363 /// transmitted as the result of content negotiation.
364 ///
365 /// Location and Content-Location are different: Location indicates the
366 /// target of a redirection (or the URL of a newly created document), while
367 /// Content-Location indicates the direct URL to use to access the resource,
368 /// without the need of further content negotiation. Location is a header
369 /// associated with the response, while Content-Location is associated with
370 /// the entity returned.
371 (ContentLocation, CONTENT_LOCATION, "content-location");
372
373 /// Indicates where in a full body message a partial message belongs.
374 (ContentRange, CONTENT_RANGE, "content-range");
375
376 /// Allows controlling resources the user agent is allowed to load for a
377 /// given page.
378 ///
379 /// With a few exceptions, policies mostly involve specifying server origins
380 /// and script endpoints. This helps guard against cross-site scripting
381 /// attacks (XSS).
382 (ContentSecurityPolicy, CONTENT_SECURITY_POLICY, "content-security-policy");
383
384 /// Allows experimenting with policies by monitoring their effects.
385 ///
386 /// The HTTP Content-Security-Policy-Report-Only response header allows web
387 /// developers to experiment with policies by monitoring (but not enforcing)
388 /// their effects. These violation reports consist of JSON documents sent
389 /// via an HTTP POST request to the specified URI.
390 (ContentSecurityPolicyReportOnly, CONTENT_SECURITY_POLICY_REPORT_ONLY, "content-security-policy-report-only");
391
392 /// Used to indicate the media type of the resource.
393 ///
394 /// In responses, a Content-Type header tells the client what the content
395 /// type of the returned content actually is. Browsers will do MIME sniffing
396 /// in some cases and will not necessarily follow the value of this header;
397 /// to prevent this behavior, the header X-Content-Type-Options can be set
398 /// to nosniff.
399 ///
400 /// In requests, (such as POST or PUT), the client tells the server what
401 /// type of data is actually sent.
402 (ContentType, CONTENT_TYPE, "content-type");
403
404 /// Contains stored HTTP cookies previously sent by the server with the
405 /// Set-Cookie header.
406 ///
407 /// The Cookie header might be omitted entirely, if the privacy setting of
408 /// the browser are set to block them, for example.
409 (Cookie, COOKIE, "cookie");
410
411 /// Indicates the client's tracking preference.
412 ///
413 /// This header lets users indicate whether they would prefer privacy rather
414 /// than personalized content.
415 (Dnt, DNT, "dnt");
416
417 /// Contains the date and time at which the message was originated.
418 (Date, DATE, "date");
419
420 /// Identifier for a specific version of a resource.
421 ///
422 /// This header allows caches to be more efficient, and saves bandwidth, as
423 /// a web server does not need to send a full response if the content has
424 /// not changed. On the other side, if the content has changed, etags are
425 /// useful to help prevent simultaneous updates of a resource from
426 /// overwriting each other ("mid-air collisions").
427 ///
428 /// If the resource at a given URL changes, a new Etag value must be
429 /// generated. Etags are therefore similar to fingerprints and might also be
430 /// used for tracking purposes by some servers. A comparison of them allows
431 /// to quickly determine whether two representations of a resource are the
432 /// same, but they might also be set to persist indefinitely by a tracking
433 /// server.
434 (Etag, ETAG, "etag");
435
436 /// Indicates expectations that need to be fulfilled by the server in order
437 /// to properly handle the request.
438 ///
439 /// The only expectation defined in the specification is Expect:
440 /// 100-continue, to which the server shall respond with:
441 ///
442 /// * 100 if the information contained in the header is sufficient to cause
443 /// an immediate success,
444 ///
445 /// * 417 (Expectation Failed) if it cannot meet the expectation; or any
446 /// other 4xx status otherwise.
447 ///
448 /// For example, the server may reject a request if its Content-Length is
449 /// too large.
450 ///
451 /// No common browsers send the Expect header, but some other clients such
452 /// as cURL do so by default.
453 (Expect, EXPECT, "expect");
454
455 /// Contains the date/time after which the response is considered stale.
456 ///
457 /// Invalid dates, like the value 0, represent a date in the past and mean
458 /// that the resource is already expired.
459 ///
460 /// If there is a Cache-Control header with the "max-age" or "s-max-age"
461 /// directive in the response, the Expires header is ignored.
462 (Expires, EXPIRES, "expires");
463
464 /// Contains information from the client-facing side of proxy servers that
465 /// is altered or lost when a proxy is involved in the path of the request.
466 ///
467 /// The alternative and de-facto standard versions of this header are the
468 /// X-Forwarded-For, X-Forwarded-Host and X-Forwarded-Proto headers.
469 ///
470 /// This header is used for debugging, statistics, and generating
471 /// location-dependent content and by design it exposes privacy sensitive
472 /// information, such as the IP address of the client. Therefore the user's
473 /// privacy must be kept in mind when deploying this header.
474 (Forwarded, FORWARDED, "forwarded");
475
476 /// Contains an Internet email address for a human user who controls the
477 /// requesting user agent.
478 ///
479 /// If you are running a robotic user agent (e.g. a crawler), the From
480 /// header should be sent, so you can be contacted if problems occur on
481 /// servers, such as if the robot is sending excessive, unwanted, or invalid
482 /// requests.
483 (From, FROM, "from");
484
485 /// Specifies the domain name of the server and (optionally) the TCP port
486 /// number on which the server is listening.
487 ///
488 /// If no port is given, the default port for the service requested (e.g.,
489 /// "80" for an HTTP URL) is implied.
490 ///
491 /// A Host header field must be sent in all HTTP/1.1 request messages. A 400
492 /// (Bad Request) status code will be sent to any HTTP/1.1 request message
493 /// that lacks a Host header field or contains more than one.
494 (Host, HOST, "host");
495
496 /// Makes a request conditional based on the E-Tag.
497 ///
498 /// For GET and HEAD methods, the server will send back the requested
499 /// resource only if it matches one of the listed ETags. For PUT and other
500 /// non-safe methods, it will only upload the resource in this case.
501 ///
502 /// The comparison with the stored ETag uses the strong comparison
503 /// algorithm, meaning two files are considered identical byte to byte only.
504 /// This is weakened when the W/ prefix is used in front of the ETag.
505 ///
506 /// There are two common use cases:
507 ///
508 /// * For GET and HEAD methods, used in combination with an Range header, it
509 /// can guarantee that the new ranges requested comes from the same resource
510 /// than the previous one. If it doesn't match, then a 416 (Range Not
511 /// Satisfiable) response is returned.
512 ///
513 /// * For other methods, and in particular for PUT, If-Match can be used to
514 /// prevent the lost update problem. It can check if the modification of a
515 /// resource that the user wants to upload will not override another change
516 /// that has been done since the original resource was fetched. If the
517 /// request cannot be fulfilled, the 412 (Precondition Failed) response is
518 /// returned.
519 (IfMatch, IF_MATCH, "if-match");
520
521 /// Makes a request conditional based on the modification date.
522 ///
523 /// The If-Modified-Since request HTTP header makes the request conditional:
524 /// the server will send back the requested resource, with a 200 status,
525 /// only if it has been last modified after the given date. If the request
526 /// has not been modified since, the response will be a 304 without any
527 /// body; the Last-Modified header will contain the date of last
528 /// modification. Unlike If-Unmodified-Since, If-Modified-Since can only be
529 /// used with a GET or HEAD.
530 ///
531 /// When used in combination with If-None-Match, it is ignored, unless the
532 /// server doesn't support If-None-Match.
533 ///
534 /// The most common use case is to update a cached entity that has no
535 /// associated ETag.
536 (IfModifiedSince, IF_MODIFIED_SINCE, "if-modified-since");
537
538 /// Makes a request conditional based on the E-Tag.
539 ///
540 /// The If-None-Match HTTP request header makes the request conditional. For
541 /// GET and HEAD methods, the server will send back the requested resource,
542 /// with a 200 status, only if it doesn't have an ETag matching the given
543 /// ones. For other methods, the request will be processed only if the
544 /// eventually existing resource's ETag doesn't match any of the values
545 /// listed.
546 ///
547 /// When the condition fails for GET and HEAD methods, then the server must
548 /// return HTTP status code 304 (Not Modified). For methods that apply
549 /// server-side changes, the status code 412 (Precondition Failed) is used.
550 /// Note that the server generating a 304 response MUST generate any of the
551 /// following header fields that would have been sent in a 200 (OK) response
552 /// to the same request: Cache-Control, Content-Location, Date, ETag,
553 /// Expires, and Vary.
554 ///
555 /// The comparison with the stored ETag uses the weak comparison algorithm,
556 /// meaning two files are considered identical not only if they are
557 /// identical byte to byte, but if the content is equivalent. For example,
558 /// two pages that would differ only by the date of generation in the footer
559 /// would be considered as identical.
560 ///
561 /// When used in combination with If-Modified-Since, it has precedence (if
562 /// the server supports it).
563 ///
564 /// There are two common use cases:
565 ///
566 /// * For `GET` and `HEAD` methods, to update a cached entity that has an associated ETag.
567 /// * For other methods, and in particular for `PUT`, `If-None-Match` used with
568 /// the `*` value can be used to save a file not known to exist,
569 /// guaranteeing that another upload didn't happen before, losing the data
570 /// of the previous put; this problems is the variation of the lost update
571 /// problem.
572 (IfNoneMatch, IF_NONE_MATCH, "if-none-match");
573
574 /// Makes a request conditional based on range.
575 ///
576 /// The If-Range HTTP request header makes a range request conditional: if
577 /// the condition is fulfilled, the range request will be issued and the
578 /// server sends back a 206 Partial Content answer with the appropriate
579 /// body. If the condition is not fulfilled, the full resource is sent back,
580 /// with a 200 OK status.
581 ///
582 /// This header can be used either with a Last-Modified validator, or with
583 /// an ETag, but not with both.
584 ///
585 /// The most common use case is to resume a download, to guarantee that the
586 /// stored resource has not been modified since the last fragment has been
587 /// received.
588 (IfRange, IF_RANGE, "if-range");
589
590 /// Makes the request conditional based on the last modification date.
591 ///
592 /// The If-Unmodified-Since request HTTP header makes the request
593 /// conditional: the server will send back the requested resource, or accept
594 /// it in the case of a POST or another non-safe method, only if it has not
595 /// been last modified after the given date. If the request has been
596 /// modified after the given date, the response will be a 412 (Precondition
597 /// Failed) error.
598 ///
599 /// There are two common use cases:
600 ///
601 /// * In conjunction non-safe methods, like POST, it can be used to
602 /// implement an optimistic concurrency control, like done by some wikis:
603 /// editions are rejected if the stored document has been modified since the
604 /// original has been retrieved.
605 ///
606 /// * In conjunction with a range request with a If-Range header, it can be
607 /// used to ensure that the new fragment requested comes from an unmodified
608 /// document.
609 (IfUnmodifiedSince, IF_UNMODIFIED_SINCE, "if-unmodified-since");
610
611 /// Content-Types that are acceptable for the response.
612 (LastModified, LAST_MODIFIED, "last-modified");
613
614 /// Allows the server to point an interested client to another resource
615 /// containing metadata about the requested resource.
616 (Link, LINK, "link");
617
618 /// Indicates the URL to redirect a page to.
619 ///
620 /// The Location response header indicates the URL to redirect a page to. It
621 /// only provides a meaning when served with a 3xx status response.
622 ///
623 /// The HTTP method used to make the new request to fetch the page pointed
624 /// to by Location depends of the original method and of the kind of
625 /// redirection:
626 ///
627 /// * If 303 (See Also) responses always lead to the use of a GET method,
628 /// 307 (Temporary Redirect) and 308 (Permanent Redirect) don't change the
629 /// method used in the original request;
630 ///
631 /// * 301 (Permanent Redirect) and 302 (Found) doesn't change the method
632 /// most of the time, though older user-agents may (so you basically don't
633 /// know).
634 ///
635 /// All responses with one of these status codes send a Location header.
636 ///
637 /// Beside redirect response, messages with 201 (Created) status also
638 /// include the Location header. It indicates the URL to the newly created
639 /// resource.
640 ///
641 /// Location and Content-Location are different: Location indicates the
642 /// target of a redirection (or the URL of a newly created resource), while
643 /// Content-Location indicates the direct URL to use to access the resource
644 /// when content negotiation happened, without the need of further content
645 /// negotiation. Location is a header associated with the response, while
646 /// Content-Location is associated with the entity returned.
647 (Location, LOCATION, "location");
648
649 /// Indicates the max number of intermediaries the request should be sent
650 /// through.
651 (MaxForwards, MAX_FORWARDS, "max-forwards");
652
653 /// Indicates where a fetch originates from.
654 ///
655 /// It doesn't include any path information, but only the server name. It is
656 /// sent with CORS requests, as well as with POST requests. It is similar to
657 /// the Referer header, but, unlike this header, it doesn't disclose the
658 /// whole path.
659 (Origin, ORIGIN, "origin");
660
661 /// HTTP/1.0 header usually used for backwards compatibility.
662 ///
663 /// The Pragma HTTP/1.0 general header is an implementation-specific header
664 /// that may have various effects along the request-response chain. It is
665 /// used for backwards compatibility with HTTP/1.0 caches where the
666 /// Cache-Control HTTP/1.1 header is not yet present.
667 (Pragma, PRAGMA, "pragma");
668
669 /// Defines the authentication method that should be used to gain access to
670 /// a proxy.
671 ///
672 /// Unlike `www-authenticate`, the `proxy-authenticate` header field applies
673 /// only to the next outbound client on the response chain. This is because
674 /// only the client that chose a given proxy is likely to have the
675 /// credentials necessary for authentication. However, when multiple proxies
676 /// are used within the same administrative domain, such as office and
677 /// regional caching proxies within a large corporate network, it is common
678 /// for credentials to be generated by the user agent and passed through the
679 /// hierarchy until consumed. Hence, in such a configuration, it will appear
680 /// as if Proxy-Authenticate is being forwarded because each proxy will send
681 /// the same challenge set.
682 ///
683 /// The `proxy-authenticate` header is sent along with a `407 Proxy
684 /// Authentication Required`.
685 (ProxyAuthenticate, PROXY_AUTHENTICATE, "proxy-authenticate");
686
687 /// Contains the credentials to authenticate a user agent to a proxy server.
688 ///
689 /// This header is usually included after the server has responded with a
690 /// 407 Proxy Authentication Required status and the Proxy-Authenticate
691 /// header.
692 (ProxyAuthorization, PROXY_AUTHORIZATION, "proxy-authorization");
693
694 /// Associates a specific cryptographic public key with a certain server.
695 ///
696 /// This decreases the risk of MITM attacks with forged certificates. If one
697 /// or several keys are pinned and none of them are used by the server, the
698 /// browser will not accept the response as legitimate, and will not display
699 /// it.
700 (PublicKeyPins, PUBLIC_KEY_PINS, "public-key-pins");
701
702 /// Sends reports of pinning violation to the report-uri specified in the
703 /// header.
704 ///
705 /// Unlike `Public-Key-Pins`, this header still allows browsers to connect
706 /// to the server if the pinning is violated.
707 (PublicKeyPinsReportOnly, PUBLIC_KEY_PINS_REPORT_ONLY, "public-key-pins-report-only");
708
709 /// Indicates the part of a document that the server should return.
710 ///
711 /// Several parts can be requested with one Range header at once, and the
712 /// server may send back these ranges in a multipart document. If the server
713 /// sends back ranges, it uses the 206 Partial Content for the response. If
714 /// the ranges are invalid, the server returns the 416 Range Not Satisfiable
715 /// error. The server can also ignore the Range header and return the whole
716 /// document with a 200 status code.
717 (Range, RANGE, "range");
718
719 /// Contains the address of the previous web page from which a link to the
720 /// currently requested page was followed.
721 ///
722 /// The Referer header allows servers to identify where people are visiting
723 /// them from and may use that data for analytics, logging, or optimized
724 /// caching, for example.
725 (Referer, REFERER, "referer");
726
727 /// Governs which referrer information should be included with requests
728 /// made.
729 (ReferrerPolicy, REFERRER_POLICY, "referrer-policy");
730
731 /// Informs the web browser that the current page or frame should be
732 /// refreshed.
733 (Refresh, REFRESH, "refresh");
734
735 /// The Retry-After response HTTP header indicates how long the user agent
736 /// should wait before making a follow-up request. There are two main cases
737 /// this header is used:
738 ///
739 /// * When sent with a 503 (Service Unavailable) response, it indicates how
740 /// long the service is expected to be unavailable.
741 ///
742 /// * When sent with a redirect response, such as 301 (Moved Permanently),
743 /// it indicates the minimum time that the user agent is asked to wait
744 /// before issuing the redirected request.
745 (RetryAfter, RETRY_AFTER, "retry-after");
746
747 /// The |Sec-WebSocket-Accept| header field is used in the WebSocket
748 /// opening handshake. It is sent from the server to the client to
749 /// confirm that the server is willing to initiate the WebSocket
750 /// connection.
751 (SecWebSocketAccept, SEC_WEBSOCKET_ACCEPT, "sec-websocket-accept");
752
753 /// The |Sec-WebSocket-Extensions| header field is used in the WebSocket
754 /// opening handshake. It is initially sent from the client to the
755 /// server, and then subsequently sent from the server to the client, to
756 /// agree on a set of protocol-level extensions to use for the duration
757 /// of the connection.
758 (SecWebSocketExtensions, SEC_WEBSOCKET_EXTENSIONS, "sec-websocket-extensions");
759
760 /// The |Sec-WebSocket-Key| header field is used in the WebSocket opening
761 /// handshake. It is sent from the client to the server to provide part
762 /// of the information used by the server to prove that it received a
763 /// valid WebSocket opening handshake. This helps ensure that the server
764 /// does not accept connections from non-WebSocket clients (e.g., HTTP
765 /// clients) that are being abused to send data to unsuspecting WebSocket
766 /// servers.
767 (SecWebSocketKey, SEC_WEBSOCKET_KEY, "sec-websocket-key");
768
769 /// The |Sec-WebSocket-Protocol| header field is used in the WebSocket
770 /// opening handshake. It is sent from the client to the server and back
771 /// from the server to the client to confirm the subprotocol of the
772 /// connection. This enables scripts to both select a subprotocol and be
773 /// sure that the server agreed to serve that subprotocol.
774 (SecWebSocketProtocol, SEC_WEBSOCKET_PROTOCOL, "sec-websocket-protocol");
775
776 /// The |Sec-WebSocket-Version| header field is used in the WebSocket
777 /// opening handshake. It is sent from the client to the server to
778 /// indicate the protocol version of the connection. This enables
779 /// servers to correctly interpret the opening handshake and subsequent
780 /// data being sent from the data, and close the connection if the server
781 /// cannot interpret that data in a safe manner.
782 (SecWebSocketVersion, SEC_WEBSOCKET_VERSION, "sec-websocket-version");
783
784 /// Contains information about the software used by the origin server to
785 /// handle the request.
786 ///
787 /// Overly long and detailed Server values should be avoided as they
788 /// potentially reveal internal implementation details that might make it
789 /// (slightly) easier for attackers to find and exploit known security
790 /// holes.
791 (Server, SERVER, "server");
792
793 /// Used to send cookies from the server to the user agent.
794 (SetCookie, SET_COOKIE, "set-cookie");
795
796 /// Tells the client to communicate with HTTPS instead of using HTTP.
797 (StrictTransportSecurity, STRICT_TRANSPORT_SECURITY, "strict-transport-security");
798
799 /// Informs the server of transfer encodings willing to be accepted as part
800 /// of the response.
801 ///
802 /// See also the Transfer-Encoding response header for more details on
803 /// transfer encodings. Note that chunked is always acceptable for HTTP/1.1
804 /// recipients and you that don't have to specify "chunked" using the TE
805 /// header. However, it is useful for setting if the client is accepting
806 /// trailer fields in a chunked transfer coding using the "trailers" value.
807 (Te, TE, "te");
808
809 /// Allows the sender to include additional fields at the end of chunked
810 /// messages.
811 (Trailer, TRAILER, "trailer");
812
813 /// Specifies the form of encoding used to safely transfer the entity to the
814 /// client.
815 ///
816 /// `transfer-encoding` is a hop-by-hop header, that is applying to a
817 /// message between two nodes, not to a resource itself. Each segment of a
818 /// multi-node connection can use different `transfer-encoding` values. If
819 /// you want to compress data over the whole connection, use the end-to-end
820 /// header `content-encoding` header instead.
821 ///
822 /// When present on a response to a `HEAD` request that has no body, it
823 /// indicates the value that would have applied to the corresponding `GET`
824 /// message.
825 (TransferEncoding, TRANSFER_ENCODING, "transfer-encoding");
826
827 /// Contains a string that allows identifying the requesting client's
828 /// software.
829 (UserAgent, USER_AGENT, "user-agent");
830
831 /// Used as part of the exchange to upgrade the protocol.
832 (Upgrade, UPGRADE, "upgrade");
833
834 /// Sends a signal to the server expressing the client’s preference for an
835 /// encrypted and authenticated response.
836 (UpgradeInsecureRequests, UPGRADE_INSECURE_REQUESTS, "upgrade-insecure-requests");
837
838 /// Determines how to match future requests with cached responses.
839 ///
840 /// The `vary` HTTP response header determines how to match future request
841 /// headers to decide whether a cached response can be used rather than
842 /// requesting a fresh one from the origin server. It is used by the server
843 /// to indicate which headers it used when selecting a representation of a
844 /// resource in a content negotiation algorithm.
845 ///
846 /// The `vary` header should be set on a 304 Not Modified response exactly
847 /// like it would have been set on an equivalent 200 OK response.
848 (Vary, VARY, "vary");
849
850 /// Added by proxies to track routing.
851 ///
852 /// The `via` general header is added by proxies, both forward and reverse
853 /// proxies, and can appear in the request headers and the response headers.
854 /// It is used for tracking message forwards, avoiding request loops, and
855 /// identifying the protocol capabilities of senders along the
856 /// request/response chain.
857 (Via, VIA, "via");
858
859 /// General HTTP header contains information about possible problems with
860 /// the status of the message.
861 ///
862 /// More than one `warning` header may appear in a response. Warning header
863 /// fields can in general be applied to any message, however some warn-codes
864 /// are specific to caches and can only be applied to response messages.
865 (Warning, WARNING, "warning");
866
867 /// Defines the authentication method that should be used to gain access to
868 /// a resource.
869 (WwwAuthenticate, WWW_AUTHENTICATE, "www-authenticate");
870
871 /// Marker used by the server to indicate that the MIME types advertised in
872 /// the `content-type` headers should not be changed and be followed.
873 ///
874 /// This allows to opt-out of MIME type sniffing, or, in other words, it is
875 /// a way to say that the webmasters knew what they were doing.
876 ///
877 /// This header was introduced by Microsoft in IE 8 as a way for webmasters
878 /// to block content sniffing that was happening and could transform
879 /// non-executable MIME types into executable MIME types. Since then, other
880 /// browsers have introduced it, even if their MIME sniffing algorithms were
881 /// less aggressive.
882 ///
883 /// Site security testers usually expect this header to be set.
884 (XContentTypeOptions, X_CONTENT_TYPE_OPTIONS, "x-content-type-options");
885
886 /// Controls DNS prefetching.
887 ///
888 /// The `x-dns-prefetch-control` HTTP response header controls DNS
889 /// prefetching, a feature by which browsers proactively perform domain name
890 /// resolution on both links that the user may choose to follow as well as
891 /// URLs for items referenced by the document, including images, CSS,
892 /// JavaScript, and so forth.
893 ///
894 /// This prefetching is performed in the background, so that the DNS is
895 /// likely to have been resolved by the time the referenced items are
896 /// needed. This reduces latency when the user clicks a link.
897 (XDnsPrefetchControl, X_DNS_PREFETCH_CONTROL, "x-dns-prefetch-control");
898
899 /// Indicates whether or not a browser should be allowed to render a page in
900 /// a frame.
901 ///
902 /// Sites can use this to avoid clickjacking attacks, by ensuring that their
903 /// content is not embedded into other sites.
904 ///
905 /// The added security is only provided if the user accessing the document
906 /// is using a browser supporting `x-frame-options`.
907 (XFrameOptions, X_FRAME_OPTIONS, "x-frame-options");
908
909 /// Stop pages from loading when an XSS attack is detected.
910 ///
911 /// The HTTP X-XSS-Protection response header is a feature of Internet
912 /// Explorer, Chrome and Safari that stops pages from loading when they
913 /// detect reflected cross-site scripting (XSS) attacks. Although these
914 /// protections are largely unnecessary in modern browsers when sites
915 /// implement a strong Content-Security-Policy that disables the use of
916 /// inline JavaScript ('unsafe-inline'), they can still provide protections
917 /// for users of older web browsers that don't yet support CSP.
918 (XXssProtection, X_XSS_PROTECTION, "x-xss-protection");
919}
920
921#[cfg(test)]
922mod tests {
923 use std::collections::HashSet;
924
925 use super::CaselessStr;
926
927 #[test]
928 fn test_caseless_str() {
929 assert_eq!(CaselessStr("test"), CaselessStr("TEST"));
930 let mut set = HashSet::new();
931 set.insert(CaselessStr("tESt"));
932 assert!(set.contains(&CaselessStr("test")));
933 assert!(set.contains(&CaselessStr("TEST")));
934 assert!(set.contains(&CaselessStr("tESt")));
935 assert!(set.replace(CaselessStr("test")).is_some());
936 assert!(set.contains(&CaselessStr("TEST")));
937 assert_eq!(set.len(), 1);
938 assert_eq!(set.get(&CaselessStr("Test")).map(|x| x.0), Some("test"))
939 }
940}