rune_axum_redirect_https/lib.rs
1//! HTTP-to-HTTPS redirect middleware for Axum and Tower.
2//!
3//! A [`tower::Layer`] that detects incoming HTTP requests and issues a
4//! permanent redirect to the HTTPS equivalent. HTTPS requests are forwarded
5//! to the inner service unchanged.
6//!
7//! Detection follows this priority order:
8//!
9//! 1. `X-Forwarded-Proto: http` — set by most reverse proxies when the
10//! upstream connection is plain HTTP.
11//! 2. URI scheme of `http` — present in direct (non-proxy) connections.
12//!
13//! If neither indicator is present the request passes through unchanged,
14//! which is the safe default when the protocol cannot be determined.
15//!
16//! # Features
17//!
18//! - Configurable redirect status: `308 Permanent Redirect` (default,
19//! method-preserving) or `301 Moved Permanently` (legacy compatibility).
20//! - Optional HTTPS port override for non-standard port setups.
21//! - Graceful fallback: if no `Host` header is present the request is
22//! forwarded rather than returning a malformed redirect without `Location`.
23//!
24//! # Quick Start
25//!
26//! ```rust,no_run
27//! use axum::{routing::get, Router};
28//! use rune_axum_redirect_https::RedirectHttpsLayer;
29//!
30//! let app: Router = Router::new()
31//! .route("/", get(|| async { "hello" }))
32//! .layer(RedirectHttpsLayer::default());
33//! ```
34//!
35//! # Custom Configuration
36//!
37//! ```rust,no_run
38//! use axum::{routing::get, Router};
39//! use http::StatusCode;
40//! use rune_axum_redirect_https::{RedirectHttps, RedirectHttpsLayer};
41//!
42//! // HTTP on :8080 → HTTPS on :8443, using 301 for legacy clients
43//! let layer = RedirectHttpsLayer::new(
44//! RedirectHttps::new()
45//! .status(StatusCode::MOVED_PERMANENTLY)
46//! .https_port(8443),
47//! );
48//!
49//! let app: Router = Router::new()
50//! .route("/", get(|| async { "hello" }))
51//! .layer(layer);
52//! ```
53
54pub use layer::{RedirectHttps, RedirectHttpsLayer};
55
56mod layer;