diff --git a/.github/workflows/CI.yml b/.github/workflows/CI.yml
index 97babe78..2c307695 100644
--- a/.github/workflows/CI.yml
+++ b/.github/workflows/CI.yml
@@ -69,7 +69,7 @@ jobs:
runs-on: ubuntu-latest
strategy:
matrix:
- rust: [stable, beta, nightly, 1.51]
+ rust: [stable, beta, nightly, 1.54]
steps:
- uses: actions/checkout@master
- uses: actions-rs/toolchain@v1
diff --git a/README.md b/README.md
index 0973f825..8a53a1c5 100644
--- a/README.md
+++ b/README.md
@@ -107,7 +107,7 @@ This crate uses `#![forbid(unsafe_code)]` to ensure everything is implemented in
## Minimum supported Rust version
-axum's MSRV is 1.51.
+axum 0.2's MSRV is 1.51. axum 0.3's (still work-in-progress) MSRV will be 1.54.
## Examples
diff --git a/src/docs/applying_middleware.md b/src/docs/applying_middleware.md
new file mode 100644
index 00000000..42246dee
--- /dev/null
+++ b/src/docs/applying_middleware.md
@@ -0,0 +1,253 @@
+# Applying middleware
+
+axum is designed to take full advantage of the tower and tower-http
+ecosystem of middleware.
+
+If you're new to tower we recommend you read its [guides][tower-guides] for
+a general introduction to tower and its concepts.
+
+## To individual handlers
+
+A middleware can be applied to a single handler like so:
+
+```rust,no_run
+use axum::{
+ handler::Handler,
+ routing::get,
+ Router,
+};
+use tower::limit::ConcurrencyLimitLayer;
+
+let app = Router::new()
+ .route(
+ "/",
+ get(handler.layer(ConcurrencyLimitLayer::new(100))),
+ );
+
+async fn handler() {}
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+## To groups of routes
+
+Middleware can also be applied to a group of routes like so:
+
+```rust,no_run
+use axum::{
+ routing::{get, post},
+ Router,
+};
+use tower::limit::ConcurrencyLimitLayer;
+
+async fn handler() {}
+
+let app = Router::new()
+ .route("/", get(handler))
+ .route("/foo", post(handler))
+ .layer(ConcurrencyLimitLayer::new(100));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+Note that [`Router::layer`] applies the middleware to all previously added
+routes, of that particular `Router`. If you need multiple groups of routes
+with different middleware build them separately and combine them with
+[`Router::merge`]:
+
+```rust,no_run
+use axum::{
+ routing::{get, post},
+ Router,
+};
+use tower::limit::ConcurrencyLimitLayer;
+# type MyAuthLayer = tower::layer::util::Identity;
+
+async fn handler() {}
+
+let foo = Router::new()
+ .route("/", get(handler))
+ .route("/foo", post(handler))
+ .layer(ConcurrencyLimitLayer::new(100));
+
+let bar = Router::new()
+ .route("/requires-auth", get(handler))
+ .layer(MyAuthLayer::new());
+
+let app = foo.merge(bar);
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+## Applying multiple middleware
+
+[`tower::ServiceBuilder`] can be used to combine multiple middleware:
+
+```rust,no_run
+use axum::{
+ body::Body,
+ routing::get,
+ http::{Request, StatusCode},
+ error_handling::HandleErrorLayer,
+ response::IntoResponse,
+ Router, BoxError,
+};
+use tower::ServiceBuilder;
+use tower_http::compression::CompressionLayer;
+use std::{borrow::Cow, time::Duration};
+
+let middleware_stack = ServiceBuilder::new()
+ // Handle errors from middleware
+ //
+ // This middleware most be added above any fallible
+ // ones if you're using `ServiceBuilder`, due to how ordering works
+ .layer(HandleErrorLayer::new(handle_error))
+ // Return an error after 30 seconds
+ .timeout(Duration::from_secs(30))
+ // Shed load if we're receiving too many requests
+ .load_shed()
+ // Process at most 100 requests concurrently
+ .concurrency_limit(100)
+ // Compress response bodies
+ .layer(CompressionLayer::new());
+
+let app = Router::new()
+ .route("/", get(|_: Request
| async { /* ... */ }))
+ .layer(middleware_stack);
+
+fn handle_error(error: BoxError) -> impl IntoResponse {
+ (
+ StatusCode::INTERNAL_SERVER_ERROR,
+ format!("Something went wrong: {}", error),
+ )
+}
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+See [Error handling](#error-handling) for more details on general error handling in axum.
+
+## Commonly used middleware
+
+[`tower::util`] and [`tower_http`] have a large collection of middleware that are compatible
+with axum. Some commonly used are:
+
+```rust,no_run
+use axum::{
+ body::{Body, BoxBody},
+ routing::get,
+ http::{Request, Response},
+ error_handling::HandleErrorLayer,
+ Router,
+};
+use tower::{
+ filter::AsyncFilterLayer,
+ util::AndThenLayer,
+ ServiceBuilder,
+};
+use std::convert::Infallible;
+use tower_http::trace::TraceLayer;
+#
+# fn handle_error(error: T) -> axum::http::StatusCode {
+# axum::http::StatusCode::INTERNAL_SERVER_ERROR
+# }
+
+let middleware_stack = ServiceBuilder::new()
+ // Handle errors from middleware
+ //
+ // This middleware most be added above any fallible
+ // ones if you're using `ServiceBuilder`, due to how ordering works
+ .layer(HandleErrorLayer::new(handle_error))
+ // `TraceLayer` adds high level tracing and logging
+ .layer(TraceLayer::new_for_http())
+ // `AsyncFilterLayer` lets you asynchronously transform the request
+ .layer(AsyncFilterLayer::new(map_request))
+ // `AndThenLayer` lets you asynchronously transform the response
+ .layer(AndThenLayer::new(map_response));
+
+async fn map_request(req: Request) -> Result, Infallible> {
+ Ok(req)
+}
+
+async fn map_response(res: Response) -> Result, Infallible> {
+ Ok(res)
+}
+
+let app = Router::new()
+ .route("/", get(|| async { /* ... */ }))
+ .layer(middleware_stack);
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+Additionally axum provides [`extract::extractor_middleware()`] for converting any extractor into
+a middleware. Among other things, this can be useful for doing authorization. See
+[`extract::extractor_middleware()`] for more details.
+
+See [Error handling](#error-handling) for more details on general error handling in axum.
+
+## Writing your own middleware
+
+You can also write you own middleware by implementing [`tower::Service`]:
+
+```
+use axum::{
+ body::{Body, BoxBody},
+ routing::get,
+ http::{Request, Response},
+ Router,
+};
+use futures::future::BoxFuture;
+use tower::{Service, layer::layer_fn};
+use std::task::{Context, Poll};
+
+#[derive(Clone)]
+struct MyMiddleware {
+ inner: S,
+}
+
+impl Service> for MyMiddleware
+where
+ S: Service, Response = Response> + Clone + Send + 'static,
+ S::Future: Send + 'static,
+ ReqBody: Send + 'static,
+ ResBody: Send + 'static,
+{
+ type Response = S::Response;
+ type Error = S::Error;
+ type Future = BoxFuture<'static, Result>;
+
+ fn poll_ready(&mut self, cx: &mut Context<'_>) -> Poll> {
+ self.inner.poll_ready(cx)
+ }
+
+ fn call(&mut self, mut req: Request) -> Self::Future {
+ println!("`MyMiddleware` called!");
+
+ // best practice is to clone the inner service like this
+ // see https://github.com/tower-rs/tower/issues/547 for details
+ let clone = self.inner.clone();
+ let mut inner = std::mem::replace(&mut self.inner, clone);
+
+ Box::pin(async move {
+ let res: Response = inner.call(req).await?;
+
+ println!("`MyMiddleware` received the response");
+
+ Ok(res)
+ })
+ }
+}
+
+let app = Router::new()
+ .route("/", get(|| async { /* ... */ }))
+ .layer(layer_fn(|inner| MyMiddleware { inner }));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
diff --git a/src/docs/building_responses.md b/src/docs/building_responses.md
new file mode 100644
index 00000000..b8e20b44
--- /dev/null
+++ b/src/docs/building_responses.md
@@ -0,0 +1,113 @@
+# Building responses
+
+Anything that implements [`IntoResponse`](response::IntoResponse) can be
+returned from a handler:
+
+```rust,no_run
+use axum::{
+ body::Body,
+ routing::get,
+ handler::Handler,
+ http::{Request, header::{HeaderMap, HeaderName, HeaderValue}},
+ response::{IntoResponse, Html, Json, Headers},
+ Router,
+};
+use http::{StatusCode, Response, Uri};
+use serde_json::{Value, json};
+
+// We've already seen returning &'static str
+async fn plain_text() -> &'static str {
+ "foo"
+}
+
+// String works too and will get a `text/plain` content-type
+async fn plain_text_string(uri: Uri) -> String {
+ format!("Hi from {}", uri.path())
+}
+
+// Bytes will get a `application/octet-stream` content-type
+async fn bytes() -> Vec {
+ vec![1, 2, 3, 4]
+}
+
+// `()` gives an empty response
+async fn empty() {}
+
+// `StatusCode` gives an empty response with that status code
+async fn empty_with_status() -> StatusCode {
+ StatusCode::NOT_FOUND
+}
+
+// A tuple of `StatusCode` and something that implements `IntoResponse` can
+// be used to override the status code
+async fn with_status() -> (StatusCode, &'static str) {
+ (StatusCode::INTERNAL_SERVER_ERROR, "Something went wrong")
+}
+
+// A tuple of `HeaderMap` and something that implements `IntoResponse` can
+// be used to override the headers
+async fn with_headers() -> (HeaderMap, &'static str) {
+ let mut headers = HeaderMap::new();
+ headers.insert(
+ HeaderName::from_static("x-foo"),
+ HeaderValue::from_static("foo"),
+ );
+ (headers, "foo")
+}
+
+// You can also override both status and headers at the same time
+async fn with_headers_and_status() -> (StatusCode, HeaderMap, &'static str) {
+ let mut headers = HeaderMap::new();
+ headers.insert(
+ HeaderName::from_static("x-foo"),
+ HeaderValue::from_static("foo"),
+ );
+ (StatusCode::INTERNAL_SERVER_ERROR, headers, "foo")
+}
+
+// `Headers` makes building the header map easier and `impl Trait` is easier
+// so you don't have to write the whole type
+async fn with_easy_headers() -> impl IntoResponse {
+ Headers(vec![("x-foo", "foo")])
+}
+
+// `Html` gives a content-type of `text/html`
+async fn html() -> Html<&'static str> {
+ Html("Hello, World!
")
+}
+
+// `Json` gives a content-type of `application/json` and works with any type
+// that implements `serde::Serialize`
+async fn json() -> Json {
+ Json(json!({ "data": 42 }))
+}
+
+// `Result` where `T` and `E` implement `IntoResponse` is useful for
+// returning errors
+async fn result() -> Result<&'static str, StatusCode> {
+ Ok("all good")
+}
+
+// `Response` gives full control
+async fn response() -> Response {
+ Response::builder().body(Body::empty()).unwrap()
+}
+
+let app = Router::new()
+ .route("/plain_text", get(plain_text))
+ .route("/plain_text_string", get(plain_text_string))
+ .route("/bytes", get(bytes))
+ .route("/empty", get(empty))
+ .route("/empty_with_status", get(empty_with_status))
+ .route("/with_status", get(with_status))
+ .route("/with_headers", get(with_headers))
+ .route("/with_headers_and_status", get(with_headers_and_status))
+ .route("/with_easy_headers", get(with_easy_headers))
+ .route("/html", get(html))
+ .route("/json", get(json))
+ .route("/result", get(result))
+ .route("/response", get(response));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
diff --git a/src/docs/compatibility.md b/src/docs/compatibility.md
new file mode 100644
index 00000000..4634e385
--- /dev/null
+++ b/src/docs/compatibility.md
@@ -0,0 +1,4 @@
+# Compatibility
+
+axum is designed to work with [tokio] and [hyper]. Runtime and
+transport layer independence is not a goal, at least for the time being.
diff --git a/src/docs/error_handling.md b/src/docs/error_handling.md
new file mode 100644
index 00000000..1358848b
--- /dev/null
+++ b/src/docs/error_handling.md
@@ -0,0 +1,19 @@
+# Error handling
+
+In the context of axum an "error" specifically means if a [`Service`]'s
+response future resolves to `Err(Service::Error)`. That means async handler
+functions can _never_ fail since they always produce a response and their
+`Service::Error` type is [`Infallible`]. Returning statuses like 404 or 500
+are _not_ errors.
+
+axum works this way because hyper will close the connection, without sending
+a response, if an error is encountered. This is not desireable so axum makes
+it impossible to forget to handle errors.
+
+Sometimes you need to route to fallible services or apply fallible
+middleware in which case you need to handle the errors. That can be done
+using things from [`error_handling`].
+
+You can find examples here:
+- [Routing to fallible services](#routing-to-fallible-services)
+- [Applying fallible middleware](#applying-multiple-middleware)
diff --git a/src/docs/example.md b/src/docs/example.md
new file mode 100644
index 00000000..ccc060d8
--- /dev/null
+++ b/src/docs/example.md
@@ -0,0 +1,22 @@
+# Example
+
+The "Hello, World!" of axum is:
+
+```rust,no_run
+use axum::{
+ routing::get,
+ Router,
+};
+
+#[tokio::main]
+async fn main() {
+ // build our application with a single route
+ let app = Router::new().route("/", get(|| async { "Hello, World!" }));
+
+ // run it with hyper on localhost:3000
+ axum::Server::bind(&"0.0.0.0:3000".parse().unwrap())
+ .serve(app.into_make_service())
+ .await
+ .unwrap();
+}
+```
diff --git a/src/docs/examples.md b/src/docs/examples.md
new file mode 100644
index 00000000..e27d4c5b
--- /dev/null
+++ b/src/docs/examples.md
@@ -0,0 +1,4 @@
+# Examples
+
+The axum repo contains [a number of examples][examples] that show how to put all the
+pieces together.
diff --git a/src/docs/extractors.md b/src/docs/extractors.md
new file mode 100644
index 00000000..b1f61e94
--- /dev/null
+++ b/src/docs/extractors.md
@@ -0,0 +1,270 @@
+# Extractors
+
+An extractor is a type that implements [`FromRequest`]. Extractors is how
+you pick apart the incoming request to get the parts your handler needs.
+
+For example, [`extract::Json`] is an extractor that consumes the request
+body and deserializes it as JSON into some target type:
+
+```rust,no_run
+use axum::{
+ extract::Json,
+ routing::post,
+ Router,
+};
+use serde::Deserialize;
+
+let app = Router::new().route("/users", post(create_user));
+
+#[derive(Deserialize)]
+struct CreateUser {
+ email: String,
+ password: String,
+}
+
+async fn create_user(Json(payload): Json) {
+ // ...
+}
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+See the [`extract`] module for everything that can be used as an extractor.
+
+## Common extractors
+
+Some commonly used extractors are:
+
+```rust,no_run
+use axum::{
+ extract::{Json, TypedHeader, Path, Extension, Query},
+ routing::post,
+ http::{Request, header::HeaderMap},
+ body::{Bytes, Body},
+ Router,
+};
+use serde_json::Value;
+use headers::UserAgent;
+use std::collections::HashMap;
+
+// `Path` gives you the path parameters and deserializes them. See its docs for
+// more details
+async fn path(Path(user_id): Path) {}
+
+// `Query` gives you the query parameters and deserializes them.
+async fn query(Query(params): Query>) {}
+
+// `HeaderMap` gives you all the headers
+async fn headers(headers: HeaderMap) {}
+
+// `TypedHeader` can be used to extract a single header
+// note this requires you've enabled axum's `headers`
+async fn user_agent(TypedHeader(user_agent): TypedHeader) {}
+
+// `String` consumes the request body and ensures it is valid utf-8
+async fn string(body: String) {}
+
+// `Bytes` gives you the raw request body
+async fn bytes(body: Bytes) {}
+
+// We've already seen `Json` for parsing the request body as json
+async fn json(Json(payload): Json) {}
+
+// `Request` gives you the whole request for maximum control
+async fn request(request: Request) {}
+
+// `Extension` extracts data from "request extensions"
+// See the "Sharing state with handlers" section for more details
+async fn extension(Extension(state): Extension) {}
+
+#[derive(Clone)]
+struct State { /* ... */ }
+
+let app = Router::new()
+ .route("/path", post(path))
+ .route("/query", post(query))
+ .route("/user_agent", post(user_agent))
+ .route("/headers", post(headers))
+ .route("/string", post(string))
+ .route("/bytes", post(bytes))
+ .route("/json", post(json))
+ .route("/request", post(request))
+ .route("/extension", post(extension));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+## Applying multiple extractors
+
+You can also apply multiple extractors:
+
+```rust,no_run
+use axum::{
+ extract,
+ routing::get,
+ Router,
+};
+use uuid::Uuid;
+use serde::Deserialize;
+
+let app = Router::new().route("/users/:id/things", get(get_user_things));
+
+#[derive(Deserialize)]
+struct Pagination {
+ page: usize,
+ per_page: usize,
+}
+
+impl Default for Pagination {
+ fn default() -> Self {
+ Self { page: 1, per_page: 30 }
+ }
+}
+
+async fn get_user_things(
+ extract::Path(user_id): extract::Path,
+ pagination: Option>,
+) {
+ let pagination: Pagination = pagination.unwrap_or_default().0;
+
+ // ...
+}
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+Take care of the order in which you apply extractors as some extractors
+mutate the request.
+
+For example using [`HeaderMap`] as an extractor will make the headers
+inaccessible for other extractors on the handler. If you need to extract
+individual headers _and_ a [`HeaderMap`] make sure to apply the extractor of
+individual headers first:
+
+```rust,no_run
+use axum::{
+ extract::TypedHeader,
+ routing::get,
+ http::header::HeaderMap,
+ Router,
+};
+use headers::UserAgent;
+
+async fn handler(
+ TypedHeader(user_agent): TypedHeader,
+ all_headers: HeaderMap,
+) {
+ // ...
+}
+
+let app = Router::new().route("/", get(handler));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+Extractors that consume the request body can also only be applied once as
+well as [`Request`], which consumes the entire request:
+
+```rust,no_run
+use axum::{
+ routing::get,
+ http::Request,
+ body::Body,
+ Router,
+};
+
+async fn handler(request: Request) {
+ // ...
+}
+
+let app = Router::new().route("/", get(handler));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+Extractors always run in the order of the function parameters that is from
+left to right.
+
+## Optional extractors
+
+All extractors defined in axum will reject the request if it doesn't match.
+If you wish to make an extractor optional you can wrap it in `Option`:
+
+```rust,no_run
+use axum::{
+ extract::Json,
+ routing::post,
+ Router,
+};
+use serde_json::Value;
+
+async fn create_user(payload: Option>) {
+ if let Some(payload) = payload {
+ // We got a valid JSON payload
+ } else {
+ // Payload wasn't valid JSON
+ }
+}
+
+let app = Router::new().route("/users", post(create_user));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+Wrapping extractors in `Result` makes them optional and gives you the reason
+the extraction failed:
+
+```rust,no_run
+use axum::{
+ extract::{Json, rejection::JsonRejection},
+ routing::post,
+ Router,
+};
+use serde_json::Value;
+
+async fn create_user(payload: Result, JsonRejection>) {
+ match payload {
+ Ok(payload) => {
+ // We got a valid JSON payload
+ }
+ Err(JsonRejection::MissingJsonContentType(_)) => {
+ // Request didn't have `Content-Type: application/json`
+ // header
+ }
+ Err(JsonRejection::InvalidJsonBody(_)) => {
+ // Couldn't deserialize the body into the target type
+ }
+ Err(JsonRejection::BodyAlreadyExtracted(_)) => {
+ // Another extractor had already consumed the body
+ }
+ Err(_) => {
+ // `JsonRejection` is marked `#[non_exhaustive]` so match must
+ // include a catch-all case.
+ }
+ }
+}
+
+let app = Router::new().route("/users", post(create_user));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+## Customizing extractor responses
+
+If an extractor fails it will return a response with the error and your
+handler will not be called. To customize the error response you have a two
+options:
+
+1. Use `Result` as your extractor like shown in ["Optional
+ extractors"](#optional-extractors). This works well if you're only using
+ the extractor in a single handler.
+2. Create your own extractor that in its [`FromRequest`] implemention calls
+ one of axum's built in extractors but returns a different response for
+ rejections. See the [customize-extractor-error] example for more details.
diff --git a/src/docs/feature_flags.md b/src/docs/feature_flags.md
new file mode 100644
index 00000000..090261eb
--- /dev/null
+++ b/src/docs/feature_flags.md
@@ -0,0 +1,15 @@
+# Feature flags
+
+axum uses a set of [feature flags] to reduce the amount of compiled and
+optional dependencies.
+
+The following optional features are available:
+
+- `headers`: Enables extracting typed headers via [`extract::TypedHeader`].
+- `http1`: Enables hyper's `http1` feature. Enabled by default.
+- `http2`: Enables hyper's `http2` feature.
+- `json`: Enables the [`Json`] type and some similar convenience functionality.
+ Enabled by default.
+- `multipart`: Enables parsing `multipart/form-data` requests with [`extract::Multipart`].
+- `tower-log`: Enables `tower`'s `log` feature. Enabled by default.
+- `ws`: Enables WebSockets support via [`extract::ws`].
diff --git a/src/docs/handlers.md b/src/docs/handlers.md
new file mode 100644
index 00000000..18d91975
--- /dev/null
+++ b/src/docs/handlers.md
@@ -0,0 +1,68 @@
+# Handlers
+
+In axum a "handler" is an async function that accepts zero or more
+["extractors"](#extractors) as arguments and returns something that
+can be converted [into a response](#building-responses).
+
+Handlers is where your custom domain logic lives and axum applications are
+built by routing between handlers.
+
+Some examples of handlers:
+
+```rust
+use bytes::Bytes;
+use http::StatusCode;
+
+// Handler that immediately returns an empty `200 OK` response.
+async fn unit_handler() {}
+
+// Handler that immediately returns an empty `200 OK` response with a plain
+// text body.
+async fn string_handler() -> String {
+ "Hello, World!".to_string()
+}
+
+// Handler that buffers the request body and returns it.
+async fn echo(body: Bytes) -> Result {
+ if let Ok(string) = String::from_utf8(body.to_vec()) {
+ Ok(string)
+ } else {
+ Err(StatusCode::BAD_REQUEST)
+ }
+}
+```
+
+## Debugging handler type errors
+
+For a function to used as a handler it must implement the [`Handler`] trait.
+axum provides blanket implementations for functions that:
+
+- Are `async fn`s.
+- Take no more than 16 arguments that all implement [`FromRequest`].
+- Returns something that implements [`IntoResponse`].
+- If a closure is used it must implement `Clone + Send + Sync` and be
+`'static`.
+- Returns a future that is `Send`. The most common way to accidentally make a
+future `!Send` is to hold a `!Send` type across an await.
+
+Unfortunately Rust gives poor error messages if you try to use a function
+that doesn't quite match what's required by [`Handler`].
+
+You might get an error like this:
+
+```not_rust
+error[E0277]: the trait bound `fn(bool) -> impl Future {handler}: Handler<_, _>` is not satisfied
+ --> src/main.rs:13:44
+ |
+13 | let app = Router::new().route("/", get(handler));
+ | ^^^^^^^ the trait `Handler<_, _>` is not implemented for `fn(bool) -> impl Future {handler}`
+ |
+ ::: axum/src/handler/mod.rs:116:8
+ |
+116 | H: Handler,
+ | ------------- required by this bound in `axum::routing::get`
+```
+
+This error doesn't tell you _why_ your function doesn't implement
+[`Handler`]. It's possible to improve the error with the [`debug_handler`]
+proc-macro from the [axum-debug] crate.
diff --git a/src/docs/high_level_features.md b/src/docs/high_level_features.md
new file mode 100644
index 00000000..6755fa7e
--- /dev/null
+++ b/src/docs/high_level_features.md
@@ -0,0 +1,14 @@
+# High level features
+
+- Route requests to handlers with a macro free API.
+- Declaratively parse requests using extractors.
+- Simple and predictable error handling model.
+- Generate responses with minimal boilerplate.
+- Take full advantage of the [`tower`] and [`tower-http`] ecosystem of
+ middleware, services, and utilities.
+
+In particular the last point is what sets `axum` apart from other frameworks.
+`axum` doesn't have its own middleware system but instead uses
+[`tower::Service`]. This means `axum` gets timeouts, tracing, compression,
+authorization, and more, for free. It also enables you to share middleware with
+applications written using [`hyper`] or [`tonic`].
diff --git a/src/docs/required_dependencies.md b/src/docs/required_dependencies.md
new file mode 100644
index 00000000..f87540de
--- /dev/null
+++ b/src/docs/required_dependencies.md
@@ -0,0 +1,20 @@
+# Required dependencies
+
+To use axum there are a few dependencies you have pull in as well:
+
+```toml
+[dependencies]
+axum = ""
+hyper = { version = "", features = ["full"] }
+tokio = { version = "", features = ["full"] }
+tower = ""
+```
+
+The `"full"` feature for hyper and tokio isn't strictly necessary but its
+the easiest way to get started.
+
+Note that [`hyper::Server`] is re-exported by axum so if thats all you need
+then you don't have to explicitly depend on hyper.
+
+Tower isn't strictly necessary either but helpful for testing. See the
+testing example in the repo to learn more about testing axum apps.
diff --git a/src/docs/routing.md b/src/docs/routing.md
new file mode 100644
index 00000000..ca4b662e
--- /dev/null
+++ b/src/docs/routing.md
@@ -0,0 +1,286 @@
+# Routing
+
+[`Router::route`] is the main way to add routes:
+
+```rust,no_run
+use axum::{
+ routing::get,
+ Router,
+};
+
+let app = Router::new()
+ .route("/", get(get_slash).post(post_slash))
+ .route("/foo", get(get_foo));
+
+async fn get_slash() {
+ // `GET /` called
+}
+
+async fn post_slash() {
+ // `POST /` called
+}
+
+async fn get_foo() {
+ // `GET /foo` called
+}
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+Routes can also be dynamic like `/users/:id`. See [extractors](#extractors)
+for more details.
+
+You can also define routes separately and merge them with [`Router::merge`].
+
+Routes are not allowed to overlap and will panic if an overlapping route is
+added. This also means the order in which routes are added doesn't matter.
+
+## Wildcard routes
+
+axum also supports wildcard routes:
+
+```rust,no_run
+use axum::{
+ routing::get,
+ Router,
+};
+
+let app = Router::new()
+ // this matches any request that starts with `/api`
+ .route("/api/*rest", get(|| async { /* ... */ }));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+The matched path can be extracted via [`extract::Path`]:
+
+```rust,no_run
+use axum::{
+ routing::get,
+ extract::Path,
+ Router,
+};
+
+let app = Router::new().route("/api/*rest", get(|Path(rest): Path| async {
+ // `rest` will be everything after `/api`
+}));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+## Nesting routes
+
+Routes can be nested by calling [`Router::nest`](routing::Router::nest):
+
+```rust,no_run
+use axum::{
+ body::{Body, BoxBody},
+ http::Request,
+ routing::get,
+ Router,
+};
+use tower_http::services::ServeFile;
+use http::Response;
+
+fn api_routes() -> Router {
+ Router::new()
+ .route("/users", get(|_: Request| async { /* ... */ }))
+}
+
+let app = Router::new()
+ .route("/", get(|_: Request| async { /* ... */ }))
+ .nest("/api", api_routes());
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+Note that nested routes will not see the orignal request URI but instead
+have the matched prefix stripped. This is necessary for services like static
+file serving to work. Use [`OriginalUri`] if you need the original request
+URI.
+
+Nested routes are similar to wild card routes. The difference is that
+wildcard routes still see the whole URI whereas nested routes will have
+the prefix stripped.
+
+```rust
+use axum::{routing::get, http::Uri, Router};
+
+let app = Router::new()
+ .route("/foo/*rest", get(|uri: Uri| async {
+ // `uri` will contain `/foo`
+ }))
+ .nest("/bar", get(|uri: Uri| async {
+ // `uri` will _not_ contain `/bar`
+ }));
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+## Fallback routes
+
+By default axum will respond with an empty `404 Not Found` response to unhandled requests. To
+override that you can use [`Router::fallback`]:
+
+```rust
+use axum::{
+ Router,
+ routing::get,
+ handler::Handler,
+ response::IntoResponse,
+ http::{StatusCode, Uri},
+};
+
+async fn fallback(uri: Uri) -> impl IntoResponse {
+ (StatusCode::NOT_FOUND, format!("No route for {}", uri))
+}
+
+let app = Router::new()
+ .route("/foo", get(|| async { /* ... */ }))
+ .fallback(fallback.into_service());
+# async {
+# hyper::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+See [`Router::fallback`] for more details.
+
+## Routing to any [`Service`]
+
+axum also supports routing to general [`Service`]s:
+
+```rust,no_run
+use axum::{
+ Router,
+ body::Body,
+ routing::service_method_router as service,
+ error_handling::HandleErrorExt,
+ http::{Request, StatusCode},
+};
+use tower_http::services::ServeFile;
+use http::Response;
+use std::{convert::Infallible, io};
+use tower::service_fn;
+
+let app = Router::new()
+ .route(
+ // Any request to `/` goes to a service
+ "/",
+ // Services who's response body is not `axum::body::BoxBody`
+ // can be wrapped in `axum::service::any` (or one of the other routing filters)
+ // to have the response body mapped
+ service::any(service_fn(|_: Request| async {
+ let res = Response::new(Body::from("Hi from `GET /`"));
+ Ok::<_, Infallible>(res)
+ }))
+ )
+ .route(
+ "/foo",
+ // This service's response body is `axum::body::BoxBody` so
+ // it can be routed to directly.
+ service_fn(|req: Request| async move {
+ let body = Body::from(format!("Hi from `{} /foo`", req.method()));
+ let body = axum::body::box_body(body);
+ let res = Response::new(body);
+ Ok::<_, Infallible>(res)
+ })
+ )
+ .route(
+ // GET `/static/Cargo.toml` goes to a service from tower-http
+ "/static/Cargo.toml",
+ service::get(ServeFile::new("Cargo.toml"))
+ // though we must handle any potential errors
+ .handle_error(|error: io::Error| {
+ (
+ StatusCode::INTERNAL_SERVER_ERROR,
+ format!("Unhandled internal error: {}", error),
+ )
+ })
+ );
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+Routing to arbitrary services in this way has complications for backpressure
+([`Service::poll_ready`]). See the [`service`] module for more details.
+
+### Routing to fallible services
+
+Note that routing to general services has a small gotcha when it comes to
+errors. axum currently does not support mixing routes to fallible services
+with infallible handlers. For example this does _not_ compile:
+
+```compile_fail
+use axum::{
+ Router,
+ routing::{get, service_method_router as service},
+ http::{Request, Response},
+ body::Body,
+};
+use std::io;
+use tower::service_fn;
+
+let app = Router::new()
+ // this route cannot fail
+ .route("/foo", get(|| async {}))
+ // this route can fail with io::Error
+ .route(
+ "/",
+ service::get(service_fn(|_req: Request| async {
+ let contents = tokio::fs::read_to_string("some_file").await?;
+ Ok::<_, io::Error>(Response::new(Body::from(contents)))
+ })),
+ );
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+The solution is to use [`handle_error`] and handle the error from the
+service:
+
+```
+use axum::{
+ Router,
+ body::Body,
+ routing::{get, service_method_router as service},
+ response::IntoResponse,
+ http::{Request, Response},
+ error_handling::HandleErrorExt,
+};
+use std::{io, convert::Infallible};
+use tower::service_fn;
+
+let app = Router::new()
+ // this route cannot fail
+ .route("/foo", get(|| async {}))
+ // this route can fail with io::Error
+ .route(
+ "/",
+ service::get(service_fn(|_req: Request| async {
+ let contents = tokio::fs::read_to_string("some_file").await?;
+ Ok::<_, io::Error>(Response::new(Body::from(contents)))
+ }))
+ .handle_error(handle_io_error),
+ );
+
+fn handle_io_error(error: io::Error) -> impl IntoResponse {
+ // ...
+}
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
+
+In this particular case you can also handle the error directly in
+`service_fn` but that is not possible, if you're routing to a service which
+you don't control.
+
+See ["Error handling"](#error-handling) for more details on [`handle_error`]
+and error handling in general.
diff --git a/src/docs/sharing_state_with_handlers.md b/src/docs/sharing_state_with_handlers.md
new file mode 100644
index 00000000..e1266649
--- /dev/null
+++ b/src/docs/sharing_state_with_handlers.md
@@ -0,0 +1,37 @@
+# Sharing state with handlers
+
+It is common to share some state between handlers for example to share a
+pool of database connections or clients to other services. That can be done
+using the [`AddExtension`] middleware (applied with [`AddExtensionLayer`])
+and the [`extract::Extension`] extractor:
+
+```rust,no_run
+use axum::{
+ AddExtensionLayer,
+ extract,
+ routing::get,
+ Router,
+};
+use std::sync::Arc;
+
+struct State {
+ // ...
+}
+
+let shared_state = Arc::new(State { /* ... */ });
+
+let app = Router::new()
+ .route("/", get(handler))
+ .layer(AddExtensionLayer::new(shared_state));
+
+async fn handler(
+ state: extract::Extension>,
+) {
+ let state: Arc = state.0;
+
+ // ...
+}
+# async {
+# axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
+# };
+```
diff --git a/src/docs/table_of_contents.md b/src/docs/table_of_contents.md
new file mode 100644
index 00000000..bf3d5d98
--- /dev/null
+++ b/src/docs/table_of_contents.md
@@ -0,0 +1,29 @@
+# Table of contents
+
+- [High level features](#high-level-features)
+- [Compatibility](#compatibility)
+- [Handlers](#handlers)
+ - [Debugging handler type errors](#debugging-handler-type-errors)
+- [Routing](#routing)
+ - [Wildcard routes](#wildcard-routes)
+ - [Nesting routes](#nesting-routes)
+ - [Fallback routes](#fallback-routes)
+ - [Routing to any `Service`](#routing-to-any-service)
+ - [Routing to fallible services](#routing-to-fallible-services)
+- [Extractors](#extractors)
+ - [Common extractors](#common-extractors)
+ - [Applying multiple extractors](#applying-multiple-extractors)
+ - [Optional extractors](#optional-extractors)
+ - [Customizing extractor responses](#customizing-extractor-responses)
+- [Building responses](#building-responses)
+- [Error handling](#error-handling)
+- [Applying middleware](#applying-middleware)
+ - [To individual handlers](#to-individual-handlers)
+ - [To groups of routes](#to-groups-of-routes)
+ - [Applying multiple middleware](#applying-multiple-middleware)
+ - [Commonly used middleware](#commonly-used-middleware)
+ - [Writing your own middleware](#writing-your-own-middleware)
+- [Sharing state with handlers](#sharing-state-with-handlers)
+- [Required dependencies](#required-dependencies)
+- [Examples](#examples)
+- [Feature flags](#feature-flags)
diff --git a/src/lib.rs b/src/lib.rs
index 0dc1ca3b..4670f48b 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -1,1172 +1,19 @@
//! axum is a web application framework that focuses on ergonomics and modularity.
//!
-//! # Table of contents
-//!
-//! - [High level features](#high-level-features)
-//! - [Compatibility](#compatibility)
-//! - [Handlers](#handlers)
-//! - [Debugging handler type errors](#debugging-handler-type-errors)
-//! - [Routing](#routing)
-//! - [Wildcard routes](#wildcard-routes)
-//! - [Nesting routes](#nesting-routes)
-//! - [Fallback routes](#fallback-routes)
-//! - [Routing to any `Service`](#routing-to-any-service)
-//! - [Routing to fallible services](#routing-to-fallible-services)
-//! - [Extractors](#extractors)
-//! - [Common extractors](#common-extractors)
-//! - [Applying multiple extractors](#applying-multiple-extractors)
-//! - [Optional extractors](#optional-extractors)
-//! - [Customizing extractor responses](#customizing-extractor-responses)
-//! - [Building responses](#building-responses)
-//! - [Error handling](#error-handling)
-//! - [Applying middleware](#applying-middleware)
-//! - [To individual handlers](#to-individual-handlers)
-//! - [To groups of routes](#to-groups-of-routes)
-//! - [Applying multiple middleware](#applying-multiple-middleware)
-//! - [Commonly used middleware](#commonly-used-middleware)
-//! - [Writing your own middleware](#writing-your-own-middleware)
-//! - [Sharing state with handlers](#sharing-state-with-handlers)
-//! - [Required dependencies](#required-dependencies)
-//! - [Examples](#examples)
-//! - [Feature flags](#feature-flags)
-//!
-//! # High level features
-//!
-//! - Route requests to handlers with a macro free API.
-//! - Declaratively parse requests using extractors.
-//! - Simple and predictable error handling model.
-//! - Generate responses with minimal boilerplate.
-//! - Take full advantage of the [`tower`] and [`tower-http`] ecosystem of
-//! middleware, services, and utilities.
-//!
-//! In particular the last point is what sets `axum` apart from other frameworks.
-//! `axum` doesn't have its own middleware system but instead uses
-//! [`tower::Service`]. This means `axum` gets timeouts, tracing, compression,
-//! authorization, and more, for free. It also enables you to share middleware with
-//! applications written using [`hyper`] or [`tonic`].
-//!
-//! # Compatibility
-//!
-//! axum is designed to work with [tokio] and [hyper]. Runtime and
-//! transport layer independence is not a goal, at least for the time being.
-//!
-//! # Example
-//!
-//! The "Hello, World!" of axum is:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! routing::get,
-//! Router,
-//! };
-//!
-//! #[tokio::main]
-//! async fn main() {
-//! // build our application with a single route
-//! let app = Router::new().route("/", get(|| async { "Hello, World!" }));
-//!
-//! // run it with hyper on localhost:3000
-//! axum::Server::bind(&"0.0.0.0:3000".parse().unwrap())
-//! .serve(app.into_make_service())
-//! .await
-//! .unwrap();
-//! }
-//! ```
-//!
-//! # Handlers
-//!
-//! In axum a "handler" is an async function that accepts zero or more
-//! ["extractors"](#extractors) as arguments and returns something that
-//! can be converted [into a response](#building-responses).
-//!
-//! Handlers is where your custom domain logic lives and axum applications are
-//! built by routing between handlers.
-//!
-//! Some examples of handlers:
-//!
-//! ```rust
-//! use bytes::Bytes;
-//! use http::StatusCode;
-//!
-//! // Handler that immediately returns an empty `200 OK` response.
-//! async fn unit_handler() {}
-//!
-//! // Handler that immediately returns an empty `200 OK` response with a plain
-//! // text body.
-//! async fn string_handler() -> String {
-//! "Hello, World!".to_string()
-//! }
-//!
-//! // Handler that buffers the request body and returns it.
-//! async fn echo(body: Bytes) -> Result {
-//! if let Ok(string) = String::from_utf8(body.to_vec()) {
-//! Ok(string)
-//! } else {
-//! Err(StatusCode::BAD_REQUEST)
-//! }
-//! }
-//! ```
-//!
-//! ## Debugging handler type errors
-//!
-//! For a function to used as a handler it must implement the [`Handler`] trait.
-//! axum provides blanket implementations for functions that:
-//!
-//! - Are `async fn`s.
-//! - Take no more than 16 arguments that all implement [`FromRequest`].
-//! - Returns something that implements [`IntoResponse`].
-//! - If a closure is used it must implement `Clone + Send + Sync` and be
-//! `'static`.
-//! - Returns a future that is `Send`. The most common way to accidentally make a
-//! future `!Send` is to hold a `!Send` type across an await.
-//!
-//! Unfortunately Rust gives poor error messages if you try to use a function
-//! that doesn't quite match what's required by [`Handler`].
-//!
-//! You might get an error like this:
-//!
-//! ```not_rust
-//! error[E0277]: the trait bound `fn(bool) -> impl Future {handler}: Handler<_, _>` is not satisfied
-//! --> src/main.rs:13:44
-//! |
-//! 13 | let app = Router::new().route("/", get(handler));
-//! | ^^^^^^^ the trait `Handler<_, _>` is not implemented for `fn(bool) -> impl Future {handler}`
-//! |
-//! ::: axum/src/handler/mod.rs:116:8
-//! |
-//! 116 | H: Handler,
-//! | ------------- required by this bound in `axum::routing::get`
-//! ```
-//!
-//! This error doesn't tell you _why_ your function doesn't implement
-//! [`Handler`]. It's possible to improve the error with the [`debug_handler`]
-//! proc-macro from the [axum-debug] crate.
-//!
-//! # Routing
-//!
-//! [`Router::route`] is the main way to add routes:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! routing::get,
-//! Router,
-//! };
-//!
-//! let app = Router::new()
-//! .route("/", get(get_slash).post(post_slash))
-//! .route("/foo", get(get_foo));
-//!
-//! async fn get_slash() {
-//! // `GET /` called
-//! }
-//!
-//! async fn post_slash() {
-//! // `POST /` called
-//! }
-//!
-//! async fn get_foo() {
-//! // `GET /foo` called
-//! }
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! Routes can also be dynamic like `/users/:id`. See [extractors](#extractors)
-//! for more details.
-//!
-//! You can also define routes separately and merge them with [`Router::merge`].
-//!
-//! Routes are not allowed to overlap and will panic if an overlapping route is
-//! added. This also means the order in which routes are added doesn't matter.
-//!
-//! ## Wildcard routes
-//!
-//! axum also supports wildcard routes:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! routing::get,
-//! Router,
-//! };
-//!
-//! let app = Router::new()
-//! // this matches any request that starts with `/api`
-//! .route("/api/*rest", get(|| async { /* ... */ }));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! The matched path can be extracted via [`extract::Path`]:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! routing::get,
-//! extract::Path,
-//! Router,
-//! };
-//!
-//! let app = Router::new().route("/api/*rest", get(|Path(rest): Path| async {
-//! // `rest` will be everything after `/api`
-//! }));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! ## Nesting routes
-//!
-//! Routes can be nested by calling [`Router::nest`](routing::Router::nest):
-//!
-//! ```rust,no_run
-//! use axum::{
-//! body::{Body, BoxBody},
-//! http::Request,
-//! routing::get,
-//! Router,
-//! };
-//! use tower_http::services::ServeFile;
-//! use http::Response;
-//!
-//! fn api_routes() -> Router {
-//! Router::new()
-//! .route("/users", get(|_: Request| async { /* ... */ }))
-//! }
-//!
-//! let app = Router::new()
-//! .route("/", get(|_: Request| async { /* ... */ }))
-//! .nest("/api", api_routes());
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! Note that nested routes will not see the orignal request URI but instead
-//! have the matched prefix stripped. This is necessary for services like static
-//! file serving to work. Use [`OriginalUri`] if you need the original request
-//! URI.
-//!
-//! Nested routes are similar to wild card routes. The difference is that
-//! wildcard routes still see the whole URI whereas nested routes will have
-//! the prefix stripped.
-//!
-//! ```rust
-//! use axum::{routing::get, http::Uri, Router};
-//!
-//! let app = Router::new()
-//! .route("/foo/*rest", get(|uri: Uri| async {
-//! // `uri` will contain `/foo`
-//! }))
-//! .nest("/bar", get(|uri: Uri| async {
-//! // `uri` will _not_ contain `/bar`
-//! }));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! ## Fallback routes
-//!
-//! By default axum will respond with an empty `404 Not Found` response to unhandled requests. To
-//! override that you can use [`Router::fallback`]:
-//!
-//! ```rust
-//! use axum::{
-//! Router,
-//! routing::get,
-//! handler::Handler,
-//! response::IntoResponse,
-//! http::{StatusCode, Uri},
-//! };
-//!
-//! async fn fallback(uri: Uri) -> impl IntoResponse {
-//! (StatusCode::NOT_FOUND, format!("No route for {}", uri))
-//! }
-//!
-//! let app = Router::new()
-//! .route("/foo", get(|| async { /* ... */ }))
-//! .fallback(fallback.into_service());
-//! # async {
-//! # hyper::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! See [`Router::fallback`] for more details.
-//!
-//! ## Routing to any [`Service`]
-//!
-//! axum also supports routing to general [`Service`]s:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! Router,
-//! body::Body,
-//! routing::service_method_router as service,
-//! error_handling::HandleErrorExt,
-//! http::{Request, StatusCode},
-//! };
-//! use tower_http::services::ServeFile;
-//! use http::Response;
-//! use std::{convert::Infallible, io};
-//! use tower::service_fn;
-//!
-//! let app = Router::new()
-//! .route(
-//! // Any request to `/` goes to a service
-//! "/",
-//! // Services who's response body is not `axum::body::BoxBody`
-//! // can be wrapped in `axum::service::any` (or one of the other routing filters)
-//! // to have the response body mapped
-//! service::any(service_fn(|_: Request| async {
-//! let res = Response::new(Body::from("Hi from `GET /`"));
-//! Ok::<_, Infallible>(res)
-//! }))
-//! )
-//! .route(
-//! "/foo",
-//! // This service's response body is `axum::body::BoxBody` so
-//! // it can be routed to directly.
-//! service_fn(|req: Request| async move {
-//! let body = Body::from(format!("Hi from `{} /foo`", req.method()));
-//! let body = axum::body::box_body(body);
-//! let res = Response::new(body);
-//! Ok::<_, Infallible>(res)
-//! })
-//! )
-//! .route(
-//! // GET `/static/Cargo.toml` goes to a service from tower-http
-//! "/static/Cargo.toml",
-//! service::get(ServeFile::new("Cargo.toml"))
-//! // though we must handle any potential errors
-//! .handle_error(|error: io::Error| {
-//! (
-//! StatusCode::INTERNAL_SERVER_ERROR,
-//! format!("Unhandled internal error: {}", error),
-//! )
-//! })
-//! );
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! Routing to arbitrary services in this way has complications for backpressure
-//! ([`Service::poll_ready`]). See the [`service`] module for more details.
-//!
-//! ### Routing to fallible services
-//!
-//! Note that routing to general services has a small gotcha when it comes to
-//! errors. axum currently does not support mixing routes to fallible services
-//! with infallible handlers. For example this does _not_ compile:
-//!
-//! ```compile_fail
-//! use axum::{
-//! Router,
-//! routing::{get, service_method_router as service},
-//! http::{Request, Response},
-//! body::Body,
-//! };
-//! use std::io;
-//! use tower::service_fn;
-//!
-//! let app = Router::new()
-//! // this route cannot fail
-//! .route("/foo", get(|| async {}))
-//! // this route can fail with io::Error
-//! .route(
-//! "/",
-//! service::get(service_fn(|_req: Request| async {
-//! let contents = tokio::fs::read_to_string("some_file").await?;
-//! Ok::<_, io::Error>(Response::new(Body::from(contents)))
-//! })),
-//! );
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! The solution is to use [`handle_error`] and handle the error from the
-//! service:
-//!
-//! ```
-//! use axum::{
-//! Router,
-//! body::Body,
-//! routing::{get, service_method_router as service},
-//! response::IntoResponse,
-//! http::{Request, Response},
-//! error_handling::HandleErrorExt,
-//! };
-//! use std::{io, convert::Infallible};
-//! use tower::service_fn;
-//!
-//! let app = Router::new()
-//! // this route cannot fail
-//! .route("/foo", get(|| async {}))
-//! // this route can fail with io::Error
-//! .route(
-//! "/",
-//! service::get(service_fn(|_req: Request| async {
-//! let contents = tokio::fs::read_to_string("some_file").await?;
-//! Ok::<_, io::Error>(Response::new(Body::from(contents)))
-//! }))
-//! .handle_error(handle_io_error),
-//! );
-//!
-//! fn handle_io_error(error: io::Error) -> impl IntoResponse {
-//! // ...
-//! }
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! In this particular case you can also handle the error directly in
-//! `service_fn` but that is not possible, if you're routing to a service which
-//! you don't control.
-//!
-//! See ["Error handling"](#error-handling) for more details on [`handle_error`]
-//! and error handling in general.
-//!
-//! # Extractors
-//!
-//! An extractor is a type that implements [`FromRequest`]. Extractors is how
-//! you pick apart the incoming request to get the parts your handler needs.
-//!
-//! For example, [`extract::Json`] is an extractor that consumes the request
-//! body and deserializes it as JSON into some target type:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! extract::Json,
-//! routing::post,
-//! Router,
-//! };
-//! use serde::Deserialize;
-//!
-//! let app = Router::new().route("/users", post(create_user));
-//!
-//! #[derive(Deserialize)]
-//! struct CreateUser {
-//! email: String,
-//! password: String,
-//! }
-//!
-//! async fn create_user(Json(payload): Json) {
-//! // ...
-//! }
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! See the [`extract`] module for everything that can be used as an extractor.
-//!
-//! ## Common extractors
-//!
-//! Some commonly used extractors are:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! extract::{Json, TypedHeader, Path, Extension, Query},
-//! routing::post,
-//! http::{Request, header::HeaderMap},
-//! body::{Bytes, Body},
-//! Router,
-//! };
-//! use serde_json::Value;
-//! use headers::UserAgent;
-//! use std::collections::HashMap;
-//!
-//! // `Path` gives you the path parameters and deserializes them. See its docs for
-//! // more details
-//! async fn path(Path(user_id): Path) {}
-//!
-//! // `Query` gives you the query parameters and deserializes them.
-//! async fn query(Query(params): Query>) {}
-//!
-//! // `HeaderMap` gives you all the headers
-//! async fn headers(headers: HeaderMap) {}
-//!
-//! // `TypedHeader` can be used to extract a single header
-//! // note this requires you've enabled axum's `headers`
-//! async fn user_agent(TypedHeader(user_agent): TypedHeader) {}
-//!
-//! // `String` consumes the request body and ensures it is valid utf-8
-//! async fn string(body: String) {}
-//!
-//! // `Bytes` gives you the raw request body
-//! async fn bytes(body: Bytes) {}
-//!
-//! // We've already seen `Json` for parsing the request body as json
-//! async fn json(Json(payload): Json) {}
-//!
-//! // `Request` gives you the whole request for maximum control
-//! async fn request(request: Request) {}
-//!
-//! // `Extension` extracts data from "request extensions"
-//! // See the "Sharing state with handlers" section for more details
-//! async fn extension(Extension(state): Extension) {}
-//!
-//! #[derive(Clone)]
-//! struct State { /* ... */ }
-//!
-//! let app = Router::new()
-//! .route("/path", post(path))
-//! .route("/query", post(query))
-//! .route("/user_agent", post(user_agent))
-//! .route("/headers", post(headers))
-//! .route("/string", post(string))
-//! .route("/bytes", post(bytes))
-//! .route("/json", post(json))
-//! .route("/request", post(request))
-//! .route("/extension", post(extension));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! ## Applying multiple extractors
-//!
-//! You can also apply multiple extractors:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! extract,
-//! routing::get,
-//! Router,
-//! };
-//! use uuid::Uuid;
-//! use serde::Deserialize;
-//!
-//! let app = Router::new().route("/users/:id/things", get(get_user_things));
-//!
-//! #[derive(Deserialize)]
-//! struct Pagination {
-//! page: usize,
-//! per_page: usize,
-//! }
-//!
-//! impl Default for Pagination {
-//! fn default() -> Self {
-//! Self { page: 1, per_page: 30 }
-//! }
-//! }
-//!
-//! async fn get_user_things(
-//! extract::Path(user_id): extract::Path,
-//! pagination: Option>,
-//! ) {
-//! let pagination: Pagination = pagination.unwrap_or_default().0;
-//!
-//! // ...
-//! }
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! Take care of the order in which you apply extractors as some extractors
-//! mutate the request.
-//!
-//! For example using [`HeaderMap`] as an extractor will make the headers
-//! inaccessible for other extractors on the handler. If you need to extract
-//! individual headers _and_ a [`HeaderMap`] make sure to apply the extractor of
-//! individual headers first:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! extract::TypedHeader,
-//! routing::get,
-//! http::header::HeaderMap,
-//! Router,
-//! };
-//! use headers::UserAgent;
-//!
-//! async fn handler(
-//! TypedHeader(user_agent): TypedHeader,
-//! all_headers: HeaderMap,
-//! ) {
-//! // ...
-//! }
-//!
-//! let app = Router::new().route("/", get(handler));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! Extractors that consume the request body can also only be applied once as
-//! well as [`Request`], which consumes the entire request:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! routing::get,
-//! http::Request,
-//! body::Body,
-//! Router,
-//! };
-//!
-//! async fn handler(request: Request) {
-//! // ...
-//! }
-//!
-//! let app = Router::new().route("/", get(handler));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! Extractors always run in the order of the function parameters that is from
-//! left to right.
-//!
-//! ## Optional extractors
-//!
-//! All extractors defined in axum will reject the request if it doesn't match.
-//! If you wish to make an extractor optional you can wrap it in `Option`:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! extract::Json,
-//! routing::post,
-//! Router,
-//! };
-//! use serde_json::Value;
-//!
-//! async fn create_user(payload: Option>) {
-//! if let Some(payload) = payload {
-//! // We got a valid JSON payload
-//! } else {
-//! // Payload wasn't valid JSON
-//! }
-//! }
-//!
-//! let app = Router::new().route("/users", post(create_user));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! Wrapping extractors in `Result` makes them optional and gives you the reason
-//! the extraction failed:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! extract::{Json, rejection::JsonRejection},
-//! routing::post,
-//! Router,
-//! };
-//! use serde_json::Value;
-//!
-//! async fn create_user(payload: Result, JsonRejection>) {
-//! match payload {
-//! Ok(payload) => {
-//! // We got a valid JSON payload
-//! }
-//! Err(JsonRejection::MissingJsonContentType(_)) => {
-//! // Request didn't have `Content-Type: application/json`
-//! // header
-//! }
-//! Err(JsonRejection::InvalidJsonBody(_)) => {
-//! // Couldn't deserialize the body into the target type
-//! }
-//! Err(JsonRejection::BodyAlreadyExtracted(_)) => {
-//! // Another extractor had already consumed the body
-//! }
-//! Err(_) => {
-//! // `JsonRejection` is marked `#[non_exhaustive]` so match must
-//! // include a catch-all case.
-//! }
-//! }
-//! }
-//!
-//! let app = Router::new().route("/users", post(create_user));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! ## Customizing extractor responses
-//!
-//! If an extractor fails it will return a response with the error and your
-//! handler will not be called. To customize the error response you have a two
-//! options:
-//!
-//! 1. Use `Result` as your extractor like shown in ["Optional
-//! extractors"](#optional-extractors). This works well if you're only using
-//! the extractor in a single handler.
-//! 2. Create your own extractor that in its [`FromRequest`] implemention calls
-//! one of axum's built in extractors but returns a different response for
-//! rejections. See the [customize-extractor-error] example for more details.
-//!
-//! # Building responses
-//!
-//! Anything that implements [`IntoResponse`](response::IntoResponse) can be
-//! returned from a handler:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! body::Body,
-//! routing::get,
-//! handler::Handler,
-//! http::{Request, header::{HeaderMap, HeaderName, HeaderValue}},
-//! response::{IntoResponse, Html, Json, Headers},
-//! Router,
-//! };
-//! use http::{StatusCode, Response, Uri};
-//! use serde_json::{Value, json};
-//!
-//! // We've already seen returning &'static str
-//! async fn plain_text() -> &'static str {
-//! "foo"
-//! }
-//!
-//! // String works too and will get a `text/plain` content-type
-//! async fn plain_text_string(uri: Uri) -> String {
-//! format!("Hi from {}", uri.path())
-//! }
-//!
-//! // Bytes will get a `application/octet-stream` content-type
-//! async fn bytes() -> Vec {
-//! vec![1, 2, 3, 4]
-//! }
-//!
-//! // `()` gives an empty response
-//! async fn empty() {}
-//!
-//! // `StatusCode` gives an empty response with that status code
-//! async fn empty_with_status() -> StatusCode {
-//! StatusCode::NOT_FOUND
-//! }
-//!
-//! // A tuple of `StatusCode` and something that implements `IntoResponse` can
-//! // be used to override the status code
-//! async fn with_status() -> (StatusCode, &'static str) {
-//! (StatusCode::INTERNAL_SERVER_ERROR, "Something went wrong")
-//! }
-//!
-//! // A tuple of `HeaderMap` and something that implements `IntoResponse` can
-//! // be used to override the headers
-//! async fn with_headers() -> (HeaderMap, &'static str) {
-//! let mut headers = HeaderMap::new();
-//! headers.insert(
-//! HeaderName::from_static("x-foo"),
-//! HeaderValue::from_static("foo"),
-//! );
-//! (headers, "foo")
-//! }
-//!
-//! // You can also override both status and headers at the same time
-//! async fn with_headers_and_status() -> (StatusCode, HeaderMap, &'static str) {
-//! let mut headers = HeaderMap::new();
-//! headers.insert(
-//! HeaderName::from_static("x-foo"),
-//! HeaderValue::from_static("foo"),
-//! );
-//! (StatusCode::INTERNAL_SERVER_ERROR, headers, "foo")
-//! }
-//!
-//! // `Headers` makes building the header map easier and `impl Trait` is easier
-//! // so you don't have to write the whole type
-//! async fn with_easy_headers() -> impl IntoResponse {
-//! Headers(vec![("x-foo", "foo")])
-//! }
-//!
-//! // `Html` gives a content-type of `text/html`
-//! async fn html() -> Html<&'static str> {
-//! Html("Hello, World!
")
-//! }
-//!
-//! // `Json` gives a content-type of `application/json` and works with any type
-//! // that implements `serde::Serialize`
-//! async fn json() -> Json {
-//! Json(json!({ "data": 42 }))
-//! }
-//!
-//! // `Result` where `T` and `E` implement `IntoResponse` is useful for
-//! // returning errors
-//! async fn result() -> Result<&'static str, StatusCode> {
-//! Ok("all good")
-//! }
-//!
-//! // `Response` gives full control
-//! async fn response() -> Response {
-//! Response::builder().body(Body::empty()).unwrap()
-//! }
-//!
-//! let app = Router::new()
-//! .route("/plain_text", get(plain_text))
-//! .route("/plain_text_string", get(plain_text_string))
-//! .route("/bytes", get(bytes))
-//! .route("/empty", get(empty))
-//! .route("/empty_with_status", get(empty_with_status))
-//! .route("/with_status", get(with_status))
-//! .route("/with_headers", get(with_headers))
-//! .route("/with_headers_and_status", get(with_headers_and_status))
-//! .route("/with_easy_headers", get(with_easy_headers))
-//! .route("/html", get(html))
-//! .route("/json", get(json))
-//! .route("/result", get(result))
-//! .route("/response", get(response));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! # Error handling
-//!
-//! In the context of axum an "error" specifically means if a [`Service`]'s
-//! response future resolves to `Err(Service::Error)`. That means async handler
-//! functions can _never_ fail since they always produce a response and their
-//! `Service::Error` type is [`Infallible`]. Returning statuses like 404 or 500
-//! are _not_ errors.
-//!
-//! axum works this way because hyper will close the connection, without sending
-//! a response, if an error is encountered. This is not desireable so axum makes
-//! it impossible to forget to handle errors.
-//!
-//! Sometimes you need to route to fallible services or apply fallible
-//! middleware in which case you need to handle the errors. That can be done
-//! using things from [`error_handling`].
-//!
-//! You can find examples here:
-//! - [Routing to fallible services](#routing-to-fallible-services)
-//! - [Applying fallible middleware](#applying-multiple-middleware)
-//!
-//! # Applying middleware
-//!
-//! axum is designed to take full advantage of the tower and tower-http
-//! ecosystem of middleware.
-//!
-//! If you're new to tower we recommend you read its [guides][tower-guides] for
-//! a general introduction to tower and its concepts.
-//!
-//! ## To individual handlers
-//!
-//! A middleware can be applied to a single handler like so:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! handler::Handler,
-//! routing::get,
-//! Router,
-//! };
-//! use tower::limit::ConcurrencyLimitLayer;
-//!
-//! let app = Router::new()
-//! .route(
-//! "/",
-//! get(handler.layer(ConcurrencyLimitLayer::new(100))),
-//! );
-//!
-//! async fn handler() {}
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! ## To groups of routes
-//!
-//! Middleware can also be applied to a group of routes like so:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! routing::{get, post},
-//! Router,
-//! };
-//! use tower::limit::ConcurrencyLimitLayer;
-//!
-//! async fn handler() {}
-//!
-//! let app = Router::new()
-//! .route("/", get(handler))
-//! .route("/foo", post(handler))
-//! .layer(ConcurrencyLimitLayer::new(100));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! Note that [`Router::layer`] applies the middleware to all previously added
-//! routes, of that particular `Router`. If you need multiple groups of routes
-//! with different middleware build them separately and combine them with
-//! [`Router::merge`]:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! routing::{get, post},
-//! Router,
-//! };
-//! use tower::limit::ConcurrencyLimitLayer;
-//! # type MyAuthLayer = tower::layer::util::Identity;
-//!
-//! async fn handler() {}
-//!
-//! let foo = Router::new()
-//! .route("/", get(handler))
-//! .route("/foo", post(handler))
-//! .layer(ConcurrencyLimitLayer::new(100));
-//!
-//! let bar = Router::new()
-//! .route("/requires-auth", get(handler))
-//! .layer(MyAuthLayer::new());
-//!
-//! let app = foo.merge(bar);
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! ## Applying multiple middleware
-//!
-//! [`tower::ServiceBuilder`] can be used to combine multiple middleware:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! body::Body,
-//! routing::get,
-//! http::{Request, StatusCode},
-//! error_handling::HandleErrorLayer,
-//! response::IntoResponse,
-//! Router, BoxError,
-//! };
-//! use tower::ServiceBuilder;
-//! use tower_http::compression::CompressionLayer;
-//! use std::{borrow::Cow, time::Duration};
-//!
-//! let middleware_stack = ServiceBuilder::new()
-//! // Handle errors from middleware
-//! //
-//! // This middleware most be added above any fallible
-//! // ones if you're using `ServiceBuilder`, due to how ordering works
-//! .layer(HandleErrorLayer::new(handle_error))
-//! // Return an error after 30 seconds
-//! .timeout(Duration::from_secs(30))
-//! // Shed load if we're receiving too many requests
-//! .load_shed()
-//! // Process at most 100 requests concurrently
-//! .concurrency_limit(100)
-//! // Compress response bodies
-//! .layer(CompressionLayer::new());
-//!
-//! let app = Router::new()
-//! .route("/", get(|_: Request| async { /* ... */ }))
-//! .layer(middleware_stack);
-//!
-//! fn handle_error(error: BoxError) -> impl IntoResponse {
-//! (
-//! StatusCode::INTERNAL_SERVER_ERROR,
-//! format!("Something went wrong: {}", error),
-//! )
-//! }
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! See [Error handling](#error-handling) for more details on general error handling in axum.
-//!
-//! ## Commonly used middleware
-//!
-//! [`tower::util`] and [`tower_http`] have a large collection of middleware that are compatible
-//! with axum. Some commonly used are:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! body::{Body, BoxBody},
-//! routing::get,
-//! http::{Request, Response},
-//! error_handling::HandleErrorLayer,
-//! Router,
-//! };
-//! use tower::{
-//! filter::AsyncFilterLayer,
-//! util::AndThenLayer,
-//! ServiceBuilder,
-//! };
-//! use std::convert::Infallible;
-//! use tower_http::trace::TraceLayer;
-//! #
-//! # fn handle_error(error: T) -> axum::http::StatusCode {
-//! # axum::http::StatusCode::INTERNAL_SERVER_ERROR
-//! # }
-//!
-//! let middleware_stack = ServiceBuilder::new()
-//! // Handle errors from middleware
-//! //
-//! // This middleware most be added above any fallible
-//! // ones if you're using `ServiceBuilder`, due to how ordering works
-//! .layer(HandleErrorLayer::new(handle_error))
-//! // `TraceLayer` adds high level tracing and logging
-//! .layer(TraceLayer::new_for_http())
-//! // `AsyncFilterLayer` lets you asynchronously transform the request
-//! .layer(AsyncFilterLayer::new(map_request))
-//! // `AndThenLayer` lets you asynchronously transform the response
-//! .layer(AndThenLayer::new(map_response));
-//!
-//! async fn map_request(req: Request) -> Result, Infallible> {
-//! Ok(req)
-//! }
-//!
-//! async fn map_response(res: Response) -> Result, Infallible> {
-//! Ok(res)
-//! }
-//!
-//! let app = Router::new()
-//! .route("/", get(|| async { /* ... */ }))
-//! .layer(middleware_stack);
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! Additionally axum provides [`extract::extractor_middleware()`] for converting any extractor into
-//! a middleware. Among other things, this can be useful for doing authorization. See
-//! [`extract::extractor_middleware()`] for more details.
-//!
-//! See [Error handling](#error-handling) for more details on general error handling in axum.
-//!
-//! ## Writing your own middleware
-//!
-//! You can also write you own middleware by implementing [`tower::Service`]:
-//!
-//! ```
-//! use axum::{
-//! body::{Body, BoxBody},
-//! routing::get,
-//! http::{Request, Response},
-//! Router,
-//! };
-//! use futures::future::BoxFuture;
-//! use tower::{Service, layer::layer_fn};
-//! use std::task::{Context, Poll};
-//!
-//! #[derive(Clone)]
-//! struct MyMiddleware {
-//! inner: S,
-//! }
-//!
-//! impl Service> for MyMiddleware
-//! where
-//! S: Service, Response = Response> + Clone + Send + 'static,
-//! S::Future: Send + 'static,
-//! ReqBody: Send + 'static,
-//! ResBody: Send + 'static,
-//! {
-//! type Response = S::Response;
-//! type Error = S::Error;
-//! type Future = BoxFuture<'static, Result>;
-//!
-//! fn poll_ready(&mut self, cx: &mut Context<'_>) -> Poll> {
-//! self.inner.poll_ready(cx)
-//! }
-//!
-//! fn call(&mut self, mut req: Request) -> Self::Future {
-//! println!("`MyMiddleware` called!");
-//!
-//! // best practice is to clone the inner service like this
-//! // see https://github.com/tower-rs/tower/issues/547 for details
-//! let clone = self.inner.clone();
-//! let mut inner = std::mem::replace(&mut self.inner, clone);
-//!
-//! Box::pin(async move {
-//! let res: Response = inner.call(req).await?;
-//!
-//! println!("`MyMiddleware` received the response");
-//!
-//! Ok(res)
-//! })
-//! }
-//! }
-//!
-//! let app = Router::new()
-//! .route("/", get(|| async { /* ... */ }))
-//! .layer(layer_fn(|inner| MyMiddleware { inner }));
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! # Sharing state with handlers
-//!
-//! It is common to share some state between handlers for example to share a
-//! pool of database connections or clients to other services. That can be done
-//! using the [`AddExtension`] middleware (applied with [`AddExtensionLayer`])
-//! and the [`extract::Extension`] extractor:
-//!
-//! ```rust,no_run
-//! use axum::{
-//! AddExtensionLayer,
-//! extract,
-//! routing::get,
-//! Router,
-//! };
-//! use std::sync::Arc;
-//!
-//! struct State {
-//! // ...
-//! }
-//!
-//! let shared_state = Arc::new(State { /* ... */ });
-//!
-//! let app = Router::new()
-//! .route("/", get(handler))
-//! .layer(AddExtensionLayer::new(shared_state));
-//!
-//! async fn handler(
-//! state: extract::Extension>,
-//! ) {
-//! let state: Arc = state.0;
-//!
-//! // ...
-//! }
-//! # async {
-//! # axum::Server::bind(&"".parse().unwrap()).serve(app.into_make_service()).await.unwrap();
-//! # };
-//! ```
-//!
-//! # Required dependencies
-//!
-//! To use axum there are a few dependencies you have pull in as well:
-//!
-//! ```toml
-//! [dependencies]
-//! axum = ""
-//! hyper = { version = "", features = ["full"] }
-//! tokio = { version = "", features = ["full"] }
-//! tower = ""
-//! ```
-//!
-//! The `"full"` feature for hyper and tokio isn't strictly necessary but its
-//! the easiest way to get started.
-//!
-//! Note that [`hyper::Server`] is re-exported by axum so if thats all you need
-//! then you don't have to explicitly depend on hyper.
-//!
-//! Tower isn't strictly necessary either but helpful for testing. See the
-//! testing example in the repo to learn more about testing axum apps.
-//!
-//! # Examples
-//!
-//! The axum repo contains [a number of examples][examples] that show how to put all the
-//! pieces together.
-//!
-//! # Feature flags
-//!
-//! axum uses a set of [feature flags] to reduce the amount of compiled and
-//! optional dependencies.
-//!
-//! The following optional features are available:
-//!
-//! - `headers`: Enables extracting typed headers via [`extract::TypedHeader`].
-//! - `http1`: Enables hyper's `http1` feature. Enabled by default.
-//! - `http2`: Enables hyper's `http2` feature.
-//! - `json`: Enables the [`Json`] type and some similar convenience functionality.
-//! Enabled by default.
-//! - `multipart`: Enables parsing `multipart/form-data` requests with [`extract::Multipart`].
-//! - `tower-log`: Enables `tower`'s `log` feature. Enabled by default.
-//! - `ws`: Enables WebSockets support via [`extract::ws`].
+#![doc = include_str!("docs/table_of_contents.md")]
+#![doc = include_str!("docs/high_level_features.md")]
+#![doc = include_str!("docs/compatibility.md")]
+#![doc = include_str!("docs/example.md")]
+#![doc = include_str!("docs/handlers.md")]
+#![doc = include_str!("docs/routing.md")]
+#![doc = include_str!("docs/extractors.md")]
+#![doc = include_str!("docs/building_responses.md")]
+#![doc = include_str!("docs/error_handling.md")]
+#![doc = include_str!("docs/applying_middleware.md")]
+#![doc = include_str!("docs/sharing_state_with_handlers.md")]
+#![doc = include_str!("docs/required_dependencies.md")]
+#![doc = include_str!("docs/examples.md")]
+#![doc = include_str!("docs/feature_flags.md")]
//!
//! [`tower`]: https://crates.io/crates/tower
//! [`tower-http`]: https://crates.io/crates/tower-http