Skip to content

"Example server" example in the docs doesn't actually run a server. #509

@kevincox

Description

@kevincox

Bug Report

The docs have a section "Example server" section which claims to "run that service using hyper."

//! # Example server
//!
//! This example shows how to apply middleware from tower-http to a [`Service`] and then run
//! that service using [hyper].
//!
//! ```rust,no_run
//! use tower_http::{
//! add_extension::AddExtensionLayer,
//! compression::CompressionLayer,
//! propagate_header::PropagateHeaderLayer,
//! sensitive_headers::SetSensitiveRequestHeadersLayer,
//! set_header::SetResponseHeaderLayer,
//! trace::TraceLayer,
//! validate_request::ValidateRequestHeaderLayer,
//! };
//! use tower::{ServiceBuilder, service_fn, BoxError};
//! use http::{Request, Response, header::{HeaderName, CONTENT_TYPE, AUTHORIZATION}};
//! use std::{sync::Arc, net::SocketAddr, convert::Infallible, iter::once};
//! use bytes::Bytes;
//! use http_body_util::Full;
//! # struct DatabaseConnectionPool;
//! # impl DatabaseConnectionPool {
//! # fn new() -> DatabaseConnectionPool { DatabaseConnectionPool }
//! # }
//! # fn content_length_from_response<B>(_: &http::Response<B>) -> Option<http::HeaderValue> { None }
//! # async fn update_in_flight_requests_metric(count: usize) {}
//!
//! // Our request handler. This is where we would implement the application logic
//! // for responding to HTTP requests...
//! async fn handler(request: Request<Full<Bytes>>) -> Result<Response<Full<Bytes>>, BoxError> {
//! // ...
//! # todo!()
//! }
//!
//! // Shared state across all request handlers --- in this case, a pool of database connections.
//! struct State {
//! pool: DatabaseConnectionPool,
//! }
//!
//! #[tokio::main]
//! async fn main() {
//! // Construct the shared state.
//! let state = State {
//! pool: DatabaseConnectionPool::new(),
//! };
//!
//! // Use tower's `ServiceBuilder` API to build a stack of tower middleware
//! // wrapping our request handler.
//! let service = ServiceBuilder::new()
//! // Mark the `Authorization` request header as sensitive so it doesn't show in logs
//! .layer(SetSensitiveRequestHeadersLayer::new(once(AUTHORIZATION)))
//! // High level logging of requests and responses
//! .layer(TraceLayer::new_for_http())
//! // Share an `Arc<State>` with all requests
//! .layer(AddExtensionLayer::new(Arc::new(state)))
//! // Compress responses
//! .layer(CompressionLayer::new())
//! // Propagate `X-Request-Id`s from requests to responses
//! .layer(PropagateHeaderLayer::new(HeaderName::from_static("x-request-id")))
//! // If the response has a known size set the `Content-Length` header
//! .layer(SetResponseHeaderLayer::overriding(CONTENT_TYPE, content_length_from_response))
//! // Authorize requests using a token
//! .layer(ValidateRequestHeaderLayer::bearer("passwordlol"))
//! // Accept only application/json, application/* and */* in a request's ACCEPT header
//! .layer(ValidateRequestHeaderLayer::accept("application/json"))
//! // Wrap a `Service` in our middleware stack
//! .service_fn(handler);
//! # let mut service = service;
//! # tower::Service::call(&mut service, Request::new(Full::default()));
//! }
//! ```
//!
//! Keep in mind that while this example uses [hyper], tower-http supports any HTTP
//! client/server implementation that uses the [http] and [http-body] crates.

However this doesn't seem to use Hyper at all and doesn't actually run any server. There is just hidden code to send a request to the Service from Rust.

Description

It seems that either the wording around the example should be updated or the example should be fixed to actually run a server.

It would be nice to have a minimal server example, as it seems like right now the way to do this is to use a "full featured" framework like axum or warp just to run a tower Service.

Metadata

Metadata

Assignees

No one assigned

    Labels

    C-bugCategory: This is a bug.E-help-wantedCall for participation: Help is requested to fix this issue.T-docsTopic: documentation

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions