Rust Axum 获取完整 URI 请求

mep*_*erp 5 rust rust-axum

尝试获取完整的请求 URI(方案 + 权限 + 路径)

我找到了讨论:https://github.com/tokio-rs/axum/discussions/1149其中说 Request.uri() 应该有它。所以我尝试了以下方法:

use axum::body::Body;
use axum::http::Request;
use axum::routing::get;
use axum::Router;

async fn handler(req: Request<Body>) -> &'static str {
    println!("The request is: {}", req.uri());
    println!("The request is: {}", req.uri().scheme_str().unwrap());
    println!("The request is: {}", req.uri().authority().unwrap());

    "Hello world"
}

#[tokio::main]
async fn main() {
    let app = Router::new().route("/test", get(handler));

    axum::Server::bind(&"0.0.0.0:8080".parse().unwrap())
        .serve(app.into_make_service())
        .await
        .unwrap();
}
Run Code Online (Sandbox Code Playgroud)

运行curl -v "http://localhost:8080/test"但我得到:

The request is: /test
thread 'tokio-runtime-worker' panicked at 'called `Option::unwrap()` on a `None` value', src/main.rs:8:59
Run Code Online (Sandbox Code Playgroud)

看起来它只包含路径。

我还发现了其他讨论:https://github.com/tokio-rs/axum/discussions/858 这表明axum::http::Uri应该能够提取所有细节,但我遇到了同样的问题:

The request is: /test
thread 'tokio-runtime-worker' panicked at 'called `Option::unwrap()` on a `None` value', src/main.rs:8:59
Run Code Online (Sandbox Code Playgroud)

curl -v "http://localhost:8080/test"

The request is: /test
thread 'tokio-runtime-worker' panicked at 'called `Option::unwrap()` on a `None` value', src/main.rs:7:53
Run Code Online (Sandbox Code Playgroud)
> cargo -V
cargo 1.68.0-nightly (2381cbdb4 2022-12-23)

> rustc --version
rustc 1.68.0-nightly (ad8ae0504 2022-12-29)
Run Code Online (Sandbox Code Playgroud)

Cargo.toml

use axum::http::Uri;
use axum::routing::get;
use axum::Router;

async fn handler(uri: Uri) -> &'static str {
    println!("The request is: {}", uri);
    println!("The request is: {}", uri.scheme_str().unwrap());
    println!("The request is: {}", uri.authority().unwrap());

    "Hello world"
}

#[tokio::main]
async fn main() {
    let app = Router::new().route("/test", get(handler));

    axum::Server::bind(&"0.0.0.0:8080".parse().unwrap())
        .serve(app.into_make_service())
        .await
        .unwrap();
}
Run Code Online (Sandbox Code Playgroud)

Tod*_*.Lu 3

中仅提供Uri. 您可以使用:RequestpathHost extractor

use axum::extract::Host;
use axum::http::Request;

#[tokio::main]
async fn main() {
    // ...
    let app = Router::new()
        .route(
            "/",
            any(|Host(hostname): Host, request: Request<Body>| async move {
                format!("Hi {hostname}")
            }),
        )
        .layer(Extension(state));
    // ...
}
Run Code Online (Sandbox Code Playgroud)