http_types_2/lib.rs
1//! # Common types for HTTP operations.
2//!
3//! `http-types` provides shared types for HTTP operations. It combines a performant, streaming
4//! interface with convenient methods for creating headers, urls, and other standard HTTP types.
5//!
6//! # Example
7//!
8//! ```
9//! # fn main() -> Result<(), http_types::url::ParseError> {
10//! #
11//! use http_types::{Method, Request, Response, StatusCode};
12//!
13//! let mut req = Request::new(Method::Get, "https://example.com");
14//! req.set_body("Hello, Nori!");
15//!
16//! let mut res = Response::new(StatusCode::Ok);
17//! res.set_body("Hello, Chashu!");
18//! #
19//! # Ok(()) }
20//! ```
21//!
22//! # How does HTTP work?
23//!
24//! We couldn't possibly explain _all_ of HTTP here: there are [5 versions](enum.Version.html) of
25//! the protocol now, and lots of extensions. But, at its core, there are only a few concepts you
26//! need to know about in order to understand what this crate does.
27//!
28//! ```txt
29//! request
30//! client ----------> server
31//! <----------
32//! response
33//! ```
34//!
35//! HTTP is an [RPC protocol](https://en.wikipedia.org/wiki/Remote_procedure_call). A client
36//! creates a [`Request`](struct.Request.html) containing a [`Url`](struct.Url.html),
37//! [`Method`](struct.Method.html), [`Headers`](struct.Headers.html), and optional
38//! [`Body`](struct.Body.html) and sends this to a server. The server then decodes this `Request`,
39//! does some work, and sends back a [`Response`](struct.Response.html).
40//!
41//! The `Url` works as a way to subdivide an IP address/domain into further addressable resources.
42//! The `Method` indicates what kind of operation we're trying to perform (get something, submit
43//! something, update something, etc.)
44//!
45//! ```txt
46//! Request
47//! |-----------------|
48//! | Url |
49//! | Method |
50//! | Headers |
51//! |-----------------|
52//! | Body (optional) |
53//! |-----------------|
54//! ```
55//!
56//! A `Response` consists of a [`StatusCode`](enum.StatusCode.html),
57//! [`Headers`](struct.Headers.html), and optionally a [`Body`](struct.Body.html). The client then
58//! decodes the `Response`, and can then operate on it. Usually the first thing it does is check
59//! the status code to see if its `Request` was successful or not, and then moves on to the information contained within the headers.
60//!
61//! ```txt
62//! Response
63//! |-----------------|
64//! | StatusCode |
65//! | Headers |
66//! |-----------------|
67//! | Body (optional) |
68//! |-----------------|
69//! ```
70//!
71//! Both `Request` and `Response` include [`Headers`](struct.Headers.html). This is like key-value metadata for HTTP
72//! requests. It needs to be encoded in a specific way (all lowercase ASCII, only some special
73//! characters) so we use the [`HeaderName`](headers/struct.HeaderName.html) and
74//! [`HeaderValue`](headers/struct.HeaderValue.html) structs rather than strings to ensure that.
75//! Another interesting thing about this is that it's valid to have multiple instances of the
76//! same header name. This is why `Headers` allows inserting multiple values, and always returns a
77//! [`Vec`](https://doc.rust-lang.org/std/vec/struct.Vec.html) of headers for each key.
78//!
79//! When reading up on HTTP you might frequently hear a lot of jargon related to ther underlying
80//! protocols. But even newer HTTP versions (`HTTP/2`, `HTTP/3`) still fundamentally use the
81//! request/response model we've described so far.
82//!
83//! # The Body Type
84//!
85//! In HTTP, [`Body`](struct.Body.html) types are optional. The content of a `Body` is a stream of
86//! bytes with a specific encoding; this encoding is its [`Mime` type](struct.Mime.html). The `Mime` can
87//! be set using the [`set_content_type`](struct.Request.html#method.set_content_type) method, and
88//! there are many different possible `Mime` types.
89//!
90//! `http-types`' `Body` struct can take anything that implements
91//! [`AsyncBufRead`](https://docs.rs/futures/0.3.1/futures/io/trait.AsyncBufRead.html) and stream
92//! it out. Depending on the version of HTTP used, the underlying bytes will be transmitted
93//! differently. As a rule, if you know the size of the body it's usually more efficient to
94//! declare it up front. But if you don't, things will still work.
95
96#![deny(missing_debug_implementations, nonstandard_style)]
97#![warn(missing_docs)]
98#![allow(clippy::new_without_default)]
99#![doc(html_favicon_url = "https://yoshuawuyts.com/assets/http-rs/favicon.ico")]
100#![doc(html_logo_url = "https://yoshuawuyts.com/assets/http-rs/logo-rounded.png")]
101
102/// HTTP cookies.
103#[cfg(feature = "cookies")]
104pub mod cookies {
105 pub use cookie::*;
106}
107
108/// URL records.
109pub mod url {
110 pub use url::{
111 EncodingOverride, Host, OpaqueOrigin, Origin, ParseError, ParseOptions, PathSegmentsMut,
112 Position, SyntaxViolation, Url, UrlQuery,
113 };
114}
115
116#[macro_use]
117mod utils;
118
119pub mod auth;
120pub mod cache;
121pub mod conditional;
122pub mod content;
123pub mod headers;
124pub mod mime;
125pub mod other;
126pub mod proxies;
127pub mod server;
128pub mod trace;
129pub mod transfer;
130pub mod upgrade;
131
132mod body;
133mod error;
134mod extensions;
135mod macros;
136mod method;
137mod parse_utils;
138mod request;
139mod response;
140mod status;
141mod status_code;
142mod version;
143
144pub use body::Body;
145pub use error::{Error, Result};
146pub use method::Method;
147pub use request::Request;
148pub use response::Response;
149pub use status::Status;
150pub use status_code::StatusCode;
151pub use version::Version;
152
153#[doc(inline)]
154pub use crate::url::Url;
155
156pub mod security;
157pub mod trailers;
158
159#[cfg(feature = "hyperium_http")]
160mod hyperium_http;
161
162#[doc(inline)]
163pub use crate::extensions::Extensions;
164
165#[cfg(feature = "serde")]
166/// Traits for conversions between types.
167pub mod convert {
168 pub use serde_crate::{de::DeserializeOwned, Deserialize, Serialize};
169 #[doc(inline)]
170 pub use serde_json::json;
171}
172
173// Not public API. Referenced by macro-generated code.
174#[doc(hidden)]
175pub mod private {
176 use crate::Error;
177 pub use crate::StatusCode;
178 use core::fmt::{Debug, Display};
179 pub use core::result::Result::Err;
180
181 pub fn new_adhoc<M>(message: M) -> Error
182 where
183 M: Display + Debug + Send + Sync + 'static,
184 {
185 Error::new_adhoc(message)
186 }
187}