headers/
lib.rs

1#![deny(missing_docs)]
2#![deny(missing_debug_implementations)]
3#![cfg_attr(test, deny(warnings))]
4#![cfg_attr(all(test, feature = "nightly"), feature(test))]
5#![doc(html_root_url = "https://docs.rs/headers/0.4.0")]
6
7//! # Typed HTTP Headers
8//!
9//! hyper has the opinion that headers should be strongly-typed, because that's
10//! why we're using Rust in the first place. To set or get any header, an object
11//! must implement the `Header` trait from this module. Several common headers
12//! are already provided, such as `Host`, `ContentType`, `UserAgent`, and others.
13//!
14//! # Why Typed?
15//!
16//! Or, why not stringly-typed? Types give the following advantages:
17//!
18//! - More difficult to typo, since typos in types should be caught by the compiler
19//! - Parsing to a proper type by default
20//!
21//! # Defining Custom Headers
22//!
23//! ## Implementing the `Header` trait
24//!
25//! Consider a Do Not Track header. It can be true or false, but it represents
26//! that via the numerals `1` and `0`.
27//!
28//! ```
29//! extern crate http;
30//! extern crate headers;
31//!
32//! use headers::{Header, HeaderName, HeaderValue};
33//!
34//! struct Dnt(bool);
35//!
36//! impl Header for Dnt {
37//!     fn name() -> &'static HeaderName {
38//!          &http::header::DNT
39//!     }
40//!
41//!     fn decode<'i, I>(values: &mut I) -> Result<Self, headers::Error>
42//!     where
43//!         I: Iterator<Item = &'i HeaderValue>,
44//!     {
45//!         let value = values
46//!             .next()
47//!             .ok_or_else(headers::Error::invalid)?;
48//!
49//!         if value == "0" {
50//!             Ok(Dnt(false))
51//!         } else if value == "1" {
52//!             Ok(Dnt(true))
53//!         } else {
54//!             Err(headers::Error::invalid())
55//!         }
56//!     }
57//!
58//!     fn encode<E>(&self, values: &mut E)
59//!     where
60//!         E: Extend<HeaderValue>,
61//!     {
62//!         let s = if self.0 {
63//!             "1"
64//!         } else {
65//!             "0"
66//!         };
67//!
68//!         let value = HeaderValue::from_static(s);
69//!
70//!         values.extend(std::iter::once(value));
71//!     }
72//! }
73//! ```
74
75extern crate base64;
76extern crate bytes;
77extern crate headers_core;
78extern crate http;
79extern crate httpdate;
80extern crate mime;
81extern crate sha1;
82#[cfg(all(test, feature = "nightly"))]
83extern crate test;
84
85pub use headers_core::{Error, Header};
86
87#[doc(hidden)]
88pub use http::HeaderMap;
89
90#[doc(hidden)]
91pub use http::header::{HeaderName, HeaderValue};
92
93#[macro_use]
94mod util;
95mod common;
96mod map_ext;
97
98pub use self::common::*;
99pub use self::map_ext::HeaderMapExt;