Compare commits

...

16 Commits

Author SHA1 Message Date
Keith Cirkel 13c72292f9
Merge 98e0cc4049 into 9fb6c13a1a 2025-08-26 10:11:10 +02:00
Rob Ede 9fb6c13a1a
ci: fix msrv job 2025-08-26 08:26:49 +01:00
Rob Ede 05cfef7f4b
ci: fix msrv job 2025-08-26 08:18:34 +01:00
Rob Ede 8f3eb32a32
chore: fix justfile for msrv 2025-08-26 08:00:19 +01:00
Rob Ede ddd16ec9db
chore(actix-http): prepare release 3.11.1 2025-08-26 07:28:27 +01:00
Rob Ede 98e0cc4049
Merge branch 'master' into add-uri-typed-headers 2025-05-10 21:17:56 +01:00
Rob Ede cfaa5b24c7
Merge branch 'master' into add-uri-typed-headers 2024-10-01 05:19:11 +01:00
Keith Cirkel 66873d16b5
Merge branch 'master' into add-uri-typed-headers 2024-09-17 09:55:44 +01:00
Keith Cirkel 4f8819d277
use parens to appease linter 2024-08-21 00:18:09 +01:00
Keith Cirkel f96a21f1fa
make Uri in http::header private 2024-08-19 14:13:00 +01:00
Keith Cirkel b66866d2d1
update references and text to RFC 9110 2024-08-19 14:13:00 +01:00
Keith Cirkel bbb7258e7b
add changelog entry for TryIntoHeaderValue Uri 2024-08-19 14:12:58 +01:00
Keith Cirkel 3ff861eb29
add referer typed header 2024-08-19 14:12:39 +01:00
Keith Cirkel f5d340878c
add location typed header 2024-08-19 14:12:39 +01:00
Keith Cirkel 342242a0e7
add content-location typed header 2024-08-19 14:12:38 +01:00
Keith Cirkel 9b6a93d72c
TryIntoHeaderValue for Uri 2024-08-19 14:12:09 +01:00
14 changed files with 396 additions and 184 deletions

View File

@ -3,6 +3,6 @@ disallowed-names = [
"e", # no single letter error bindings
]
disallowed-methods = [
{ path = "std::cell::RefCell::default()", reason = "prefer explicit inner type default" },
{ path = "std::rc::Rc::default()", reason = "prefer explicit inner type default" },
{ path = "std::cell::RefCell::default()", reason = "prefer explicit inner type default (remove allow-invalid when rust-lang/rust-clippy/#8581 is fixed)", allow-invalid = true },
{ path = "std::rc::Rc::default()", reason = "prefer explicit inner type default (remove allow-invalid when rust-lang/rust-clippy/#8581 is fixed)", allow-invalid = true },
]

422
Cargo.lock generated

File diff suppressed because it is too large Load Diff

View File

@ -2,8 +2,11 @@
## Unreleased
- Update `TestRequest::set_payload` to generate "Content-Length" header
- Malformed websocket frames are now gracefully rejected.
## 3.11.1
- Prevent more hangs after client disconnects.
- More malformed WebSocket frames are now gracefully rejected.
- Using `TestRequest::set_payload()` now sets a Content-Length header.
## 3.11.0

View File

@ -1,6 +1,6 @@
[package]
name = "actix-http"
version = "3.11.0"
version = "3.11.1"
authors = ["Nikolay Kim <fafhrd91@gmail.com>", "Rob Ede <robjtede@icloud.com>"]
description = "HTTP types and services for the Actix ecosystem"
keywords = ["actix", "http", "framework", "async", "futures"]

View File

@ -5,11 +5,11 @@
<!-- prettier-ignore-start -->
[![crates.io](https://img.shields.io/crates/v/actix-http?label=latest)](https://crates.io/crates/actix-http)
[![Documentation](https://docs.rs/actix-http/badge.svg?version=3.11.0)](https://docs.rs/actix-http/3.11.0)
[![Documentation](https://docs.rs/actix-http/badge.svg?version=3.11.1)](https://docs.rs/actix-http/3.11.1)
![Version](https://img.shields.io/badge/rustc-1.72+-ab6000.svg)
![MIT or Apache 2.0 licensed](https://img.shields.io/crates/l/actix-http.svg)
<br />
[![dependency status](https://deps.rs/crate/actix-http/3.11.0/status.svg)](https://deps.rs/crate/actix-http/3.11.0)
[![dependency status](https://deps.rs/crate/actix-http/3.11.1/status.svg)](https://deps.rs/crate/actix-http/3.11.1)
[![Download](https://img.shields.io/crates/d/actix-http.svg)](https://crates.io/crates/actix-http)
[![Chat on Discord](https://img.shields.io/discord/771444961383153695?label=chat&logo=discord)](https://discord.gg/NWpN5mmg3x)

View File

@ -1,7 +1,7 @@
//! [`TryIntoHeaderValue`] trait and implementations.
use bytes::Bytes;
use http::{header::InvalidHeaderValue, Error as HttpError, HeaderValue};
use http::{header::InvalidHeaderValue, Error as HttpError, HeaderValue, Uri};
use mime::Mime;
/// An interface for types that can be converted into a [`HeaderValue`].
@ -129,3 +129,12 @@ impl TryIntoHeaderValue for Mime {
HeaderValue::from_str(self.as_ref())
}
}
impl TryIntoHeaderValue for Uri {
type Error = InvalidHeaderValue;
#[inline]
fn try_into_value(self) -> Result<HeaderValue, Self::Error> {
HeaderValue::from_str(&self.to_string())
}
}

View File

@ -13,6 +13,7 @@ macro_rules! register {
register!(finish => "(.*)", "(.*)", "(.*)", "(.*)")
}};
(finish => $p1:literal, $p2:literal, $p3:literal, $p4:literal) => {{
#[expect(clippy::useless_concat)]
let arr = [
concat!("/authorizations"),
concat!("/authorizations/", $p1),

View File

@ -35,6 +35,10 @@
- On Windows, an error is now returned from `HttpServer::bind()` (or TLS variants) when binding to a socket that's already in use.
- Update `brotli` dependency to `7`.
- Minimum supported Rust version (MSRV) is now 1.75.
- Add `TryIntoHeaderValue` for `Uri` type.
- Add `http::header::ContentLocation` typed header.
- Add `http::header::Location` typed header.
- Add `http::header::Referer` typed header.
## 4.9.0

View File

@ -3,7 +3,6 @@
- The return type for `ServiceRequest::app_data::<T>()` was changed from returning a `Data<T>` to simply a `T`. To access a `Data<T>` use `ServiceRequest::app_data::<Data<T>>()`.
- Cookie handling has been offloaded to the `cookie` crate:
- `USERINFO_ENCODE_SET` is no longer exposed. Percent-encoding is still supported; check docs.
- Some types now require lifetime parameters.

View File

@ -0,0 +1,36 @@
use super::{Uri, CONTENT_LOCATION};
crate::http::header::common_header! {
/// `Content-Location` header, defined
/// in [RFC 9110 §8.7](https://datatracker.ietf.org/doc/html/rfc9110#section-8.7)
///
/// The "Content-Location" header field references a URI that can be used
/// as an identifier for a specific resource corresponding to the
/// representation in this message's content.
///
/// # ABNF
/// ```plain
/// Content-Location = absolute-URI / partial-URI
/// ```
///
/// # Example Values
/// * `http://www.example.org/hypertext/Overview.html`
///
/// # Examples
///
/// ```
/// use actix_web::HttpResponse;
/// use actix_http::Uri;
/// use actix_web::http::header::ContentLocation;
///
/// let mut builder = HttpResponse::Created();
/// builder.insert_header(
/// ContentLocation("http://www.example.org".parse::<Uri>().unwrap())
/// );
/// ```
(ContentLocation, CONTENT_LOCATION) => [Uri]
test_parse_and_format {
crate::http::header::common_header_test!(test1, [b"http://www.example.org/hypertext/Overview.html"]);
}
}

View File

@ -0,0 +1,37 @@
use super::{Uri, LOCATION};
crate::http::header::common_header! {
/// `Location` header, defined
/// in [RFC 9110 §10.2.2](https://datatracker.ietf.org/doc/html/rfc9110#section-10.2.2)
///
/// The "Location" header field is used in some responses to refer to a
/// specific resource in relation to the response. The type of relationship
/// is defined by the combination of request method and status code
/// semantics.
///
/// # ABNF
/// ```plain
/// Location = URI-reference
/// ```
///
/// # Example Values
/// * `http://www.example.org/hypertext/Overview.html`
///
/// # Examples
///
/// ```
/// use actix_web::HttpResponse;
/// use actix_http::Uri;
/// use actix_web::http::header::Location;
///
/// let mut builder = HttpResponse::Ok();
/// builder.insert_header(
/// Location("http://www.example.org".parse::<Uri>().unwrap())
/// );
/// ```
(Location, LOCATION) => [Uri]
test_parse_and_format {
crate::http::header::common_header_test!(test1, [b"http://www.example.org/hypertext/Overview.html"]);
}
}

View File

@ -14,6 +14,7 @@ use std::fmt;
// - the few typed headers from actix-http
// - header parsing utils
pub use actix_http::header::*;
use actix_http::Uri;
use bytes::{Bytes, BytesMut};
mod accept;
@ -25,6 +26,7 @@ mod cache_control;
mod content_disposition;
mod content_language;
mod content_length;
mod content_location;
mod content_range;
mod content_type;
mod date;
@ -38,9 +40,11 @@ mod if_none_match;
mod if_range;
mod if_unmodified_since;
mod last_modified;
mod location;
mod macros;
mod preference;
mod range;
mod referer;
#[cfg(test)]
pub(crate) use self::macros::common_header_test;
@ -55,6 +59,7 @@ pub use self::{
content_disposition::{ContentDisposition, DispositionParam, DispositionType},
content_language::ContentLanguage,
content_length::ContentLength,
content_location::ContentLocation,
content_range::{ContentRange, ContentRangeSpec},
content_type::ContentType,
date::Date,
@ -68,8 +73,10 @@ pub use self::{
if_range::IfRange,
if_unmodified_since::IfUnmodifiedSince,
last_modified::LastModified,
location::Location,
preference::Preference,
range::{ByteRangeSpec, Range},
referer::Referer,
};
/// Format writer ([`fmt::Write`]) for a [`BytesMut`].

View File

@ -0,0 +1,36 @@
use super::{Uri, REFERER};
crate::http::header::common_header! {
/// `Referer` header, defined
/// in [RFC 9110 §10.1.3](https://datatracker.ietf.org/doc/html/rfc9110#section-10.1.3)
///
/// The "Referer" (sic) header field allows the user agent to specify a URI
/// reference for the resource from which the target URI was obtained (i.e.,
/// the "referrer", though the field name is misspelled).
///
/// # ABNF
/// ```plain
/// Referer = absolute-URI / partial-URI
/// ```
///
/// # Example Values
/// * `http://www.example.org/hypertext/Overview.html`
///
/// # Examples
///
/// ```
/// use actix_web::HttpResponse;
/// use actix_http::Uri;
/// use actix_web::http::header::Referer;
///
/// let mut builder = HttpResponse::Ok();
/// builder.insert_header(
/// Referer("http://www.example.org".parse::<Uri>().unwrap())
/// );
/// ```
(Referer, REFERER) => [Uri]
test_parse_and_format {
crate::http::header::common_header_test!(test1, [b"http://www.example.org/hypertext/Overview.html"]);
}
}

View File

@ -13,6 +13,8 @@ fmt:
[private]
downgrade-for-msrv:
cargo {{ toolchain }} update -p=divan --precise=0.1.15 # next ver: 1.80.0
cargo {{ toolchain }} update -p=rayon --precise=1.10.0 # next ver: 1.80.0
cargo {{ toolchain }} update -p=rayon-core --precise=1.12.1 # next ver: 1.80.0
cargo {{ toolchain }} update -p=half --precise=2.4.1 # next ver: 1.81.0
cargo {{ toolchain }} update -p=idna_adapter --precise=1.2.0 # next ver: 1.82.0
cargo {{ toolchain }} update -p=litemap --precise=0.7.4 # next ver: 1.81.0
@ -50,8 +52,7 @@ clippy:
cargo {{ toolchain }} clippy --workspace --all-targets {{ all_crate_features }}
# Run Clippy over workspace using MSRV.
clippy-msrv:
@just toolchain={{ msrv_rustup }} downgrade-for-msrv
clippy-msrv: downgrade-for-msrv
@just toolchain={{ msrv_rustup }} clippy
# Test workspace code.
@ -62,8 +63,7 @@ test:
cargo {{ toolchain }} nextest run --no-tests=warn --workspace --exclude=actix-web-codegen --exclude=actix-multipart-derive {{ all_crate_features }} --filter-expr="not test(test_reading_deflate_encoding_large_random_rustls)"
# Test workspace using MSRV.
test-msrv:
@just toolchain={{ msrv_rustup }} downgrade-for-msrv
test-msrv: downgrade-for-msrv
@just toolchain={{ msrv_rustup }} test
# Test workspace docs.