From b6ffaee0996e7b7b1d609e3110d9456e097dc0e8 Mon Sep 17 00:00:00 2001 From: Jonas Platte Date: Fri, 26 Dec 2025 14:37:53 +0100 Subject: [PATCH 1/7] Exclude broken example from workspace --- Cargo.lock | 38 -------------------------------------- Cargo.toml | 8 ++++++-- 2 files changed, 6 insertions(+), 40 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 72ece474..40d8ec75 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1216,21 +1216,6 @@ dependencies = [ "pq-sys", ] -[[package]] -name = "diesel-async" -version = "0.5.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "51a307ac00f7c23f526a04a77761a0519b9f0eb2838ebf5b905a58580095bdcb" -dependencies = [ - "async-trait", - "bb8 0.8.6", - "diesel", - "futures-util", - "scoped-futures", - "tokio", - "tokio-postgres", -] - [[package]] name = "diesel_derives" version = "2.2.7" @@ -1520,20 +1505,6 @@ dependencies = [ "uuid", ] -[[package]] -name = "example-diesel-async-postgres" -version = "0.1.0" -dependencies = [ - "axum", - "bb8 0.8.6", - "diesel", - "diesel-async", - "serde", - "tokio", - "tracing", - "tracing-subscriber", -] - [[package]] name = "example-diesel-postgres" version = "0.1.0" @@ -4514,15 +4485,6 @@ dependencies = [ "serde_json", ] -[[package]] -name = "scoped-futures" -version = "0.1.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1b24aae2d0636530f359e9d5ef0c04669d11c5e756699b27a6a6d845d8329091" -dependencies = [ - "pin-project-lite", -] - [[package]] name = "scopeguard" version = "1.2.0" diff --git a/Cargo.toml b/Cargo.toml index f2110925..ee8b6b9a 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -2,8 +2,12 @@ members = ["axum", "axum-*", "examples/*"] # Only check / build main crates by default (check all with `--workspace`) default-members = ["axum", "axum-*"] -# Example has been deleted, but README.md remains -exclude = ["examples/async-graphql"] +exclude = [ + # Example has been deleted, but README.md remains + "examples/async-graphql", + # Dependency bug, fixed on main - DO NOT MERGE + "examples/diesel-async-postgres" +] resolver = "2" [workspace.package] From 5155b9bed718cd83dcf119851922f84fe97aa209 Mon Sep 17 00:00:00 2001 From: Jonas Platte Date: Fri, 26 Dec 2025 14:38:28 +0100 Subject: [PATCH 2/7] Remove cargo-public-api-crates CI job It's broken and has been replaced on main. --- .github/workflows/CI.yml | 17 ----------------- 1 file changed, 17 deletions(-) diff --git a/.github/workflows/CI.yml b/.github/workflows/CI.yml index f6b6c4b3..f63262aa 100644 --- a/.github/workflows/CI.yml +++ b/.github/workflows/CI.yml @@ -61,23 +61,6 @@ jobs: - name: cargo hack check run: cargo hack check --each-feature --no-dev-deps --all - cargo-public-api-crates: - runs-on: ubuntu-24.04 - strategy: - matrix: - crate: [axum, axum-core, axum-extra, axum-macros] - steps: - - uses: actions/checkout@v4 - - uses: dtolnay/rust-toolchain@nightly - - uses: Swatinem/rust-cache@v2 - with: - save-if: ${{ github.ref == 'refs/heads/main' }} - - name: Install cargo-public-api-crates - run: | - cargo install --git https://github.com/jplatte/cargo-public-api-crates - - name: cargo public-api-crates check - run: cargo public-api-crates --manifest-path ${{ matrix.crate }}/Cargo.toml check - test-versions: needs: check runs-on: ubuntu-24.04 From 8eaf49e3171a4a1a4056806626d15ed5e393c7fe Mon Sep 17 00:00:00 2001 From: Jonas Platte Date: Fri, 26 Dec 2025 14:39:07 +0100 Subject: [PATCH 3/7] Remove cargo-sort CI job It isn't very important and fixing it here will result in more merge conflicts. --- .github/workflows/CI.yml | 18 ------------------ 1 file changed, 18 deletions(-) diff --git a/.github/workflows/CI.yml b/.github/workflows/CI.yml index f63262aa..52623733 100644 --- a/.github/workflows/CI.yml +++ b/.github/workflows/CI.yml @@ -209,24 +209,6 @@ jobs: --manifest-path ./examples/simple-router-wasm/Cargo.toml --target wasm32-unknown-unknown - dependencies-are-sorted: - runs-on: ubuntu-24.04 - steps: - - uses: actions/checkout@v4 - - uses: dtolnay/rust-toolchain@beta - - uses: Swatinem/rust-cache@v2 - with: - save-if: ${{ github.ref == 'refs/heads/main' }} - - name: Install cargo-sort - run: | - cargo install cargo-sort - # Work around cargo-sort not honoring workspace.exclude - - name: Remove non-crate folder - run: rm -rf examples/async-graphql - - name: Check dependency tables - run: | - cargo sort --workspace --grouped --check - typos: name: Spell Check with Typos runs-on: ubuntu-24.04 From adf2e6c6bfd9d8f611afd82cca7b3e9e916203f7 Mon Sep 17 00:00:00 2001 From: Jonas Platte Date: Fri, 26 Dec 2025 14:40:56 +0100 Subject: [PATCH 4/7] Remove CI job using ancient nightly It has been updated on main, backporting is too much effort. --- .github/workflows/CI.yml | 19 ------------------- 1 file changed, 19 deletions(-) diff --git a/.github/workflows/CI.yml b/.github/workflows/CI.yml index 52623733..28d2b521 100644 --- a/.github/workflows/CI.yml +++ b/.github/workflows/CI.yml @@ -78,25 +78,6 @@ jobs: - name: Run tests run: cargo test --workspace --all-features --all-targets - # some examples don't support our MSRV so we only test axum itself on our MSRV - test-nightly: - needs: check - runs-on: ubuntu-24.04 - steps: - - uses: actions/checkout@v4 - - name: Get rust-toolchain version - id: rust-toolchain - run: echo "version=$(cat axum-macros/rust-toolchain)" >> $GITHUB_OUTPUT - - uses: dtolnay/rust-toolchain@master - with: - toolchain: ${{ steps.rust-toolchain.outputs.version }} - - uses: Swatinem/rust-cache@v2 - with: - save-if: ${{ github.ref == 'refs/heads/main' }} - - name: Run nightly tests - working-directory: axum-macros - run: cargo test - # some examples don't support our MSRV (such as async-graphql) # so we only test axum itself on our MSRV test-msrv: From aba8046921b15e407f9f7e78bd3b2ae36a657c2b Mon Sep 17 00:00:00 2001 From: Jonas Platte Date: Fri, 26 Dec 2025 14:24:42 +0100 Subject: [PATCH 5/7] Deprecate Host and Scheme extractors --- axum-extra/src/extract/host.rs | 3 +++ axum-extra/src/extract/mod.rs | 2 ++ axum-extra/src/extract/scheme.rs | 2 ++ examples/tls-graceful-shutdown/src/main.rs | 23 +++++----------------- examples/tls-rustls/src/main.rs | 21 ++++---------------- 5 files changed, 16 insertions(+), 35 deletions(-) diff --git a/axum-extra/src/extract/host.rs b/axum-extra/src/extract/host.rs index f42018d2..edac555c 100644 --- a/axum-extra/src/extract/host.rs +++ b/axum-extra/src/extract/host.rs @@ -1,3 +1,5 @@ +#![allow(deprecated)] + use super::rejection::{FailedToResolveHost, HostRejection}; use axum_core::{ extract::{FromRequestParts, OptionalFromRequestParts}, @@ -25,6 +27,7 @@ const X_FORWARDED_HOST_HEADER_KEY: &str = "X-Forwarded-Host"; /// /// Note that user agents can set `X-Forwarded-Host` and `Host` headers to arbitrary values so make /// sure to validate them to avoid security issues. +#[deprecated = "will be removed in the next version; see https://github.com/tokio-rs/axum/issues/3442"] #[derive(Debug, Clone)] pub struct Host(pub String); diff --git a/axum-extra/src/extract/mod.rs b/axum-extra/src/extract/mod.rs index cd55ecf2..389c5f48 100644 --- a/axum-extra/src/extract/mod.rs +++ b/axum-extra/src/extract/mod.rs @@ -34,6 +34,7 @@ mod scheme; #[cfg(feature = "optional-path")] pub use self::optional_path::OptionalPath; +#[allow(deprecated)] pub use self::host::Host; #[cfg(feature = "cached")] @@ -62,6 +63,7 @@ pub use self::query::{OptionalQueryRejection, Query, QueryRejection}; #[cfg(feature = "multipart")] pub use self::multipart::Multipart; +#[allow(deprecated)] #[cfg(feature = "scheme")] #[doc(no_inline)] pub use self::scheme::{Scheme, SchemeMissing}; diff --git a/axum-extra/src/extract/scheme.rs b/axum-extra/src/extract/scheme.rs index 9d3bc0c3..267f81fd 100644 --- a/axum-extra/src/extract/scheme.rs +++ b/axum-extra/src/extract/scheme.rs @@ -1,5 +1,6 @@ //! Extractor that parses the scheme of a request. //! See [`Scheme`] for more details. +#![allow(deprecated)] use axum_core::{__define_rejection as define_rejection, extract::FromRequestParts}; use http::{ @@ -17,6 +18,7 @@ const X_FORWARDED_PROTO_HEADER_KEY: &str = "X-Forwarded-Proto"; /// /// Note that user agents can set the `X-Forwarded-Proto` header to arbitrary values so make /// sure to validate them to avoid security issues. +#[deprecated = "will be removed in the next version; see https://github.com/tokio-rs/axum/issues/3442"] #[derive(Debug, Clone)] pub struct Scheme(pub String); diff --git a/examples/tls-graceful-shutdown/src/main.rs b/examples/tls-graceful-shutdown/src/main.rs index 50256e28..9a17520b 100644 --- a/examples/tls-graceful-shutdown/src/main.rs +++ b/examples/tls-graceful-shutdown/src/main.rs @@ -6,12 +6,11 @@ use axum::{ handler::HandlerWithoutStateExt, - http::{uri::Authority, StatusCode, Uri}, + http::{StatusCode, Uri}, response::Redirect, routing::get, BoxError, Router, }; -use axum_extra::extract::Host; use axum_server::tls_rustls::RustlsConfig; use std::{future::Future, net::SocketAddr, path::PathBuf, time::Duration}; use tokio::signal; @@ -106,33 +105,21 @@ async fn redirect_http_to_https(ports: Ports, signal: F) where F: Future + Send + 'static, { - fn make_https(host: &str, uri: Uri, https_port: u16) -> Result { + fn make_https(uri: Uri, https_port: u16) -> Result { let mut parts = uri.into_parts(); parts.scheme = Some(axum::http::uri::Scheme::HTTPS); + parts.authority = Some(format!("localhost:{https_port}").parse()?); if parts.path_and_query.is_none() { parts.path_and_query = Some("/".parse().unwrap()); } - let authority: Authority = host.parse()?; - let bare_host = match authority.port() { - Some(port_struct) => authority - .as_str() - .strip_suffix(port_struct.as_str()) - .unwrap() - .strip_suffix(':') - .unwrap(), // if authority.port() is Some(port) then we can be sure authority ends with :{port} - None => authority.as_str(), - }; - - parts.authority = Some(format!("{bare_host}:{https_port}").parse()?); - Ok(Uri::from_parts(parts)?) } - let redirect = move |Host(host): Host, uri: Uri| async move { - match make_https(&host, uri, ports.https) { + let redirect = move |uri: Uri| async move { + match make_https(uri, ports.https) { Ok(uri) => Ok(Redirect::permanent(&uri.to_string())), Err(error) => { tracing::warn!(%error, "failed to convert URI to HTTPS"); diff --git a/examples/tls-rustls/src/main.rs b/examples/tls-rustls/src/main.rs index 53620eff..739de241 100644 --- a/examples/tls-rustls/src/main.rs +++ b/examples/tls-rustls/src/main.rs @@ -13,7 +13,6 @@ use axum::{ routing::get, BoxError, Router, }; -use axum_extra::extract::Host; use axum_server::tls_rustls::RustlsConfig; use std::{net::SocketAddr, path::PathBuf}; use tracing_subscriber::{layer::SubscriberExt, util::SubscriberInitExt}; @@ -72,33 +71,21 @@ async fn handler() -> &'static str { #[allow(dead_code)] async fn redirect_http_to_https(ports: Ports) { - fn make_https(host: &str, uri: Uri, https_port: u16) -> Result { + fn make_https(uri: Uri, https_port: u16) -> Result { let mut parts = uri.into_parts(); parts.scheme = Some(axum::http::uri::Scheme::HTTPS); + parts.authority = Some(format!("localhost:{https_port}").parse()?); if parts.path_and_query.is_none() { parts.path_and_query = Some("/".parse().unwrap()); } - let authority: Authority = host.parse()?; - let bare_host = match authority.port() { - Some(port_struct) => authority - .as_str() - .strip_suffix(port_struct.as_str()) - .unwrap() - .strip_suffix(':') - .unwrap(), // if authority.port() is Some(port) then we can be sure authority ends with :{port} - None => authority.as_str(), - }; - - parts.authority = Some(format!("{bare_host}:{https_port}").parse()?); - Ok(Uri::from_parts(parts)?) } - let redirect = move |Host(host): Host, uri: Uri| async move { - match make_https(&host, uri, ports.https) { + let redirect = move |uri: Uri| async move { + match make_https(uri, ports.https) { Ok(uri) => Ok(Redirect::permanent(&uri.to_string())), Err(error) => { tracing::warn!(%error, "failed to convert URI to HTTPS"); From f72c298ee8b31b5b4fdcff3f69a7481ad3b075e3 Mon Sep 17 00:00:00 2001 From: Jonas Platte Date: Sat, 20 Dec 2025 18:40:34 +0100 Subject: [PATCH 6/7] Improve error messages with #[diagnostic::do_not_recommend] (#3588) --- axum-core/src/extract/option.rs | 4 ++++ axum-core/src/extract/request_parts.rs | 3 +++ axum-core/src/extract/tuple.rs | 3 +++ .../fail/argument_not_extractor.stderr | 16 ++++++++-------- .../fail/extension_not_clone.stderr | 17 ++++++++--------- .../fail/generic_without_via.stderr | 3 --- .../fail/generic_without_via_rejection.stderr | 3 --- ...verride_rejection_on_enum_without_via.stderr | 6 ------ .../fail/parts_extracting_body.stderr | 16 ++++++++-------- axum/src/extract/nested_path.rs | 1 + axum/src/handler/mod.rs | 4 ++++ axum/src/routing/method_routing.rs | 1 + 12 files changed, 40 insertions(+), 37 deletions(-) diff --git a/axum-core/src/extract/option.rs b/axum-core/src/extract/option.rs index c537e721..0ffd277f 100644 --- a/axum-core/src/extract/option.rs +++ b/axum-core/src/extract/option.rs @@ -35,6 +35,9 @@ pub trait OptionalFromRequest: Sized { ) -> impl Future, Self::Rejection>> + Send; } +// Compiler hint just says that there is an impl for Option, not mentioning +// the bounds, which is not very helpful. +#[diagnostic::do_not_recommend] impl FromRequestParts for Option where T: OptionalFromRequestParts, @@ -50,6 +53,7 @@ where } } +#[diagnostic::do_not_recommend] impl FromRequest for Option where T: OptionalFromRequest, diff --git a/axum-core/src/extract/request_parts.rs b/axum-core/src/extract/request_parts.rs index b2a5c14a..ea6a2214 100644 --- a/axum-core/src/extract/request_parts.rs +++ b/axum-core/src/extract/request_parts.rs @@ -65,6 +65,7 @@ where } } +#[diagnostic::do_not_recommend] // pretty niche impl impl FromRequest for BytesMut where S: Send + Sync, @@ -134,6 +135,7 @@ where } } +#[diagnostic::do_not_recommend] // pretty niche impl impl FromRequestParts for Parts where S: Send + Sync, @@ -145,6 +147,7 @@ where } } +#[diagnostic::do_not_recommend] // pretty niche impl impl FromRequestParts for Extensions where S: Send + Sync, diff --git a/axum-core/src/extract/tuple.rs b/axum-core/src/extract/tuple.rs index ccfd21d0..abbe181a 100644 --- a/axum-core/src/extract/tuple.rs +++ b/axum-core/src/extract/tuple.rs @@ -3,6 +3,7 @@ use crate::response::{IntoResponse, Response}; use http::request::Parts; use std::{convert::Infallible, future::Future}; +#[diagnostic::do_not_recommend] impl FromRequestParts for () where S: Send + Sync, @@ -18,6 +19,7 @@ macro_rules! impl_from_request { ( [$($ty:ident),*], $last:ident ) => { + #[diagnostic::do_not_recommend] #[allow(non_snake_case, unused_mut, unused_variables)] impl FromRequestParts for ($($ty,)* $last,) where @@ -43,6 +45,7 @@ macro_rules! impl_from_request { // This impl must not be generic over M, otherwise it would conflict with the blanket // implementation of `FromRequest` for `T: FromRequestParts`. + #[diagnostic::do_not_recommend] #[allow(non_snake_case, unused_mut, unused_variables)] impl FromRequest for ($($ty,)* $last,) where diff --git a/axum-macros/tests/debug_handler/fail/argument_not_extractor.stderr b/axum-macros/tests/debug_handler/fail/argument_not_extractor.stderr index 56a4fff5..29cb4765 100644 --- a/axum-macros/tests/debug_handler/fail/argument_not_extractor.stderr +++ b/axum-macros/tests/debug_handler/fail/argument_not_extractor.stderr @@ -7,14 +7,14 @@ error[E0277]: the trait bound `bool: FromRequest<(), axum_core::extract::private = note: Function argument is not a valid axum extractor. See `https://docs.rs/axum/0.8/axum/extract/index.html` for details = help: the following other types implement trait `FromRequestParts`: - `()` implements `FromRequestParts` - `(T1, T2)` implements `FromRequestParts` - `(T1, T2, T3)` implements `FromRequestParts` - `(T1, T2, T3, T4)` implements `FromRequestParts` - `(T1, T2, T3, T4, T5)` implements `FromRequestParts` - `(T1, T2, T3, T4, T5, T6)` implements `FromRequestParts` - `(T1, T2, T3, T4, T5, T6, T7)` implements `FromRequestParts` - `(T1, T2, T3, T4, T5, T6, T7, T8)` implements `FromRequestParts` + `ConnectInfo` implements `FromRequestParts` + `Extension` implements `FromRequestParts` + `HeaderMap` implements `FromRequestParts` + `MatchedPath` implements `FromRequestParts` + `Method` implements `FromRequestParts` + `OriginalUri` implements `FromRequestParts` + `Query` implements `FromRequestParts` + `RawPathParams` implements `FromRequestParts` and $N others = note: required for `bool` to implement `FromRequest<(), axum_core::extract::private::ViaParts>` note: required by a bound in `__axum_macros_check_handler_0_from_request_check` diff --git a/axum-macros/tests/debug_handler/fail/extension_not_clone.stderr b/axum-macros/tests/debug_handler/fail/extension_not_clone.stderr index 81bec918..1e13b8e4 100644 --- a/axum-macros/tests/debug_handler/fail/extension_not_clone.stderr +++ b/axum-macros/tests/debug_handler/fail/extension_not_clone.stderr @@ -5,15 +5,14 @@ error[E0277]: the trait bound `NonCloneType: Clone` is not satisfied | ^^^^^^^^^^^^^^^^^^^^^^^ the trait `Clone` is not implemented for `NonCloneType`, which is required by `Extension: FromRequest<(), _>` | = help: the following other types implement trait `FromRequest`: - (T1, T2) - (T1, T2, T3) - (T1, T2, T3, T4) - (T1, T2, T3, T4, T5) - (T1, T2, T3, T4, T5, T6) - (T1, T2, T3, T4, T5, T6, T7) - (T1, T2, T3, T4, T5, T6, T7, T8) - (T1, T2, T3, T4, T5, T6, T7, T8, T9) - and $N others + Body + Form + Json + RawForm + Result>::Rejection> + String + axum::body::Bytes + axum::http::Request = note: required for `Extension` to implement `FromRequestParts<()>` = note: required for `Extension` to implement `FromRequest<(), axum_core::extract::private::ViaParts>` note: required by a bound in `__axum_macros_check_test_extension_non_clone_0_from_request_check` diff --git a/axum-macros/tests/from_request/fail/generic_without_via.stderr b/axum-macros/tests/from_request/fail/generic_without_via.stderr index daabab09..ecb18877 100644 --- a/axum-macros/tests/from_request/fail/generic_without_via.stderr +++ b/axum-macros/tests/from_request/fail/generic_without_via.stderr @@ -13,9 +13,6 @@ error[E0277]: the trait bound `fn(Extractor<()>) -> impl Future {fo | required by a bound introduced by this call | = note: Consider using `#[axum::debug_handler]` to improve the error message - = help: the following other types implement trait `Handler`: - `Layered` implements `Handler` - `MethodRouter` implements `Handler<(), S>` note: required by a bound in `axum::routing::get` --> $WORKSPACE/axum/src/routing/method_routing.rs | diff --git a/axum-macros/tests/from_request/fail/generic_without_via_rejection.stderr b/axum-macros/tests/from_request/fail/generic_without_via_rejection.stderr index 66f90281..c162a915 100644 --- a/axum-macros/tests/from_request/fail/generic_without_via_rejection.stderr +++ b/axum-macros/tests/from_request/fail/generic_without_via_rejection.stderr @@ -13,9 +13,6 @@ error[E0277]: the trait bound `fn(Extractor<()>) -> impl Future {fo | required by a bound introduced by this call | = note: Consider using `#[axum::debug_handler]` to improve the error message - = help: the following other types implement trait `Handler`: - `Layered` implements `Handler` - `MethodRouter` implements `Handler<(), S>` note: required by a bound in `axum::routing::get` --> $WORKSPACE/axum/src/routing/method_routing.rs | diff --git a/axum-macros/tests/from_request/fail/override_rejection_on_enum_without_via.stderr b/axum-macros/tests/from_request/fail/override_rejection_on_enum_without_via.stderr index e70248f3..418b5a05 100644 --- a/axum-macros/tests/from_request/fail/override_rejection_on_enum_without_via.stderr +++ b/axum-macros/tests/from_request/fail/override_rejection_on_enum_without_via.stderr @@ -13,9 +13,6 @@ error[E0277]: the trait bound `fn(MyExtractor) -> impl Future {hand | required by a bound introduced by this call | = note: Consider using `#[axum::debug_handler]` to improve the error message - = help: the following other types implement trait `Handler`: - `Layered` implements `Handler` - `MethodRouter` implements `Handler<(), S>` note: required by a bound in `axum::routing::get` --> $WORKSPACE/axum/src/routing/method_routing.rs | @@ -35,9 +32,6 @@ error[E0277]: the trait bound `fn(Result) -> impl Futu | required by a bound introduced by this call | = note: Consider using `#[axum::debug_handler]` to improve the error message - = help: the following other types implement trait `Handler`: - `Layered` implements `Handler` - `MethodRouter` implements `Handler<(), S>` note: required by a bound in `MethodRouter::::post` --> $WORKSPACE/axum/src/routing/method_routing.rs | diff --git a/axum-macros/tests/from_request/fail/parts_extracting_body.stderr b/axum-macros/tests/from_request/fail/parts_extracting_body.stderr index 3008270f..10a832be 100644 --- a/axum-macros/tests/from_request/fail/parts_extracting_body.stderr +++ b/axum-macros/tests/from_request/fail/parts_extracting_body.stderr @@ -7,12 +7,12 @@ error[E0277]: the trait bound `String: FromRequestParts<_>` is not satisfied = note: Function argument is not a valid axum extractor. See `https://docs.rs/axum/0.8/axum/extract/index.html` for details = help: the following other types implement trait `FromRequestParts`: - `()` implements `FromRequestParts` - `(T1, T2)` implements `FromRequestParts` - `(T1, T2, T3)` implements `FromRequestParts` - `(T1, T2, T3, T4)` implements `FromRequestParts` - `(T1, T2, T3, T4, T5)` implements `FromRequestParts` - `(T1, T2, T3, T4, T5, T6)` implements `FromRequestParts` - `(T1, T2, T3, T4, T5, T6, T7)` implements `FromRequestParts` - `(T1, T2, T3, T4, T5, T6, T7, T8)` implements `FromRequestParts` + `ConnectInfo` implements `FromRequestParts` + `Extension` implements `FromRequestParts` + `Extractor` implements `FromRequestParts` + `HeaderMap` implements `FromRequestParts` + `MatchedPath` implements `FromRequestParts` + `Method` implements `FromRequestParts` + `OriginalUri` implements `FromRequestParts` + `Query` implements `FromRequestParts` and $N others diff --git a/axum/src/extract/nested_path.rs b/axum/src/extract/nested_path.rs index 1d2c255e..713f03ee 100644 --- a/axum/src/extract/nested_path.rs +++ b/axum/src/extract/nested_path.rs @@ -47,6 +47,7 @@ impl NestedPath { } } +#[diagnostic::do_not_recommend] // pretty niche type impl FromRequestParts for NestedPath where S: Send + Sync, diff --git a/axum/src/handler/mod.rs b/axum/src/handler/mod.rs index e99be5f8..36c06b8d 100644 --- a/axum/src/handler/mod.rs +++ b/axum/src/handler/mod.rs @@ -204,6 +204,7 @@ pub trait Handler: Clone + Send + Sync + Sized + 'static { } } +#[diagnostic::do_not_recommend] impl Handler<((),), S> for F where F: FnOnce() -> Fut + Clone + Send + Sync + 'static, @@ -221,6 +222,7 @@ macro_rules! impl_handler { ( [$($ty:ident),*], $last:ident ) => { + #[diagnostic::do_not_recommend] #[allow(non_snake_case, unused_mut)] impl Handler<(M, $($ty,)* $last,), S> for F where @@ -265,6 +267,7 @@ mod private { pub enum IntoResponseHandler {} } +#[diagnostic::do_not_recommend] impl Handler for T where T: IntoResponse + Clone + Send + Sync + 'static, @@ -310,6 +313,7 @@ where } } +#[diagnostic::do_not_recommend] impl Handler for Layered where L: Layer> + Clone + Send + Sync + 'static, diff --git a/axum/src/routing/method_routing.rs b/axum/src/routing/method_routing.rs index 5dee1e47..338d89c4 100644 --- a/axum/src/routing/method_routing.rs +++ b/axum/src/routing/method_routing.rs @@ -1306,6 +1306,7 @@ where } } +#[diagnostic::do_not_recommend] impl Handler<(), S> for MethodRouter where S: Clone + 'static, From 4e2bc8c92a570ff98dd5b774a0449092e407a942 Mon Sep 17 00:00:00 2001 From: Jonas Platte Date: Sat, 27 Dec 2025 10:35:59 +0100 Subject: [PATCH 7/7] Release axum-extra v0.12.4 --- Cargo.lock | 2 +- axum-extra/CHANGELOG.md | 8 ++++++++ axum-extra/Cargo.toml | 2 +- 3 files changed, 10 insertions(+), 2 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 40d8ec75..4bf108ed 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -362,7 +362,7 @@ dependencies = [ [[package]] name = "axum-extra" -version = "0.12.3" +version = "0.12.4" dependencies = [ "axum", "axum-core", diff --git a/axum-extra/CHANGELOG.md b/axum-extra/CHANGELOG.md index 3c30c566..84678f98 100644 --- a/axum-extra/CHANGELOG.md +++ b/axum-extra/CHANGELOG.md @@ -5,6 +5,14 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog], and this project adheres to [Semantic Versioning]. +# 0.12.4 + +- **changed:** Deprecated the `Host` and `Scheme` extractors ([#3595]) + - Please comment in [#3442] if you depend on one of them + +[#3595]: https://github.com/tokio-rs/axum/pull/3595 +[#3442]: https://github.com/tokio-rs/axum/issues/3442 + # 0.12.3 - **changed:** Make the `typed-routing` feature enable the `routing` feature ([#3514]) diff --git a/axum-extra/Cargo.toml b/axum-extra/Cargo.toml index be652623..e81e187c 100644 --- a/axum-extra/Cargo.toml +++ b/axum-extra/Cargo.toml @@ -9,7 +9,7 @@ license = "MIT" name = "axum-extra" readme = "README.md" repository = "https://github.com/tokio-rs/axum" -version = "0.12.3" +version = "0.12.4" [features] default = ["tracing"]