use axum::{extract::Path, http::StatusCode, response::IntoResponse, routing::get, Router}; use std::net::SocketAddr; async fn anon_greet() -> &'static str { "Hello World!\n" } async fn greet(Path(name): Path) -> impl IntoResponse { let greeting = String::from("He's dead, ") + name.as_str(); let greeting = greeting + &String::from("!\n"); (StatusCode::OK, greeting) } async fn health_check() -> impl IntoResponse { (StatusCode::OK, ()) } fn app() -> Router { Router::new() .route("/", get(anon_greet)) .route("/:name", get(greet)) .route("/health_check", get(health_check)) } pub async fn run() { let addr = SocketAddr::from(([127, 0, 0, 1], 3000)); tracing::info!("listening on {}", addr); axum::Server::bind(&addr) .serve(app().into_make_service()) .await .unwrap() } #[cfg(test)] mod tests { use super::*; use axum::{ body::Body, http::{Request, StatusCode}, }; use std::net::{SocketAddr, TcpListener}; #[tokio::test] async fn the_real_deal() { let listener = TcpListener::bind("127.0.0.1:0".parse::().unwrap()).unwrap(); let addr = listener.local_addr().unwrap(); tokio::spawn(async move { axum::Server::from_tcp(listener) .unwrap() .serve(app().into_make_service()) .await .unwrap(); }); let response = hyper::Client::new() .request( Request::builder() .uri(format!("http://{}/", addr)) .body(Body::empty()) .unwrap(), ) .await .unwrap(); let body = hyper::body::to_bytes(response.into_body()).await.unwrap(); assert_eq!(&body[..], b"Hello World!\n"); } }