From 61009f3a068aa43cc6b3dc965191d0fd5504edf7 Mon Sep 17 00:00:00 2001 From: Denis Cornehl Date: Wed, 3 Jan 2024 09:15:57 +0100 Subject: [PATCH] upgrade axum, hyper, http, sentry & tower-http --- Cargo.lock | 281 ++++++++++++++++++++++++++------------- Cargo.toml | 21 +-- src/cdn.rs | 18 +-- src/test/mod.rs | 35 ++--- src/web/cache.rs | 6 +- src/web/csp.rs | 4 +- src/web/headers.rs | 10 +- src/web/metrics.rs | 9 +- src/web/mod.rs | 33 +++-- src/web/page/web_page.rs | 16 +-- src/web/routes.rs | 26 ++-- src/web/source.rs | 3 +- src/web/statics.rs | 8 +- 13 files changed, 286 insertions(+), 184 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 39a7e2df3..b1ffbb92e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -217,7 +217,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fdb8867f378f33f78a811a8eb9bf108ad99430d7aad43315dd9319c827ef6247" dependencies = [ "flate2", - "http", + "http 0.2.11", "log", "native-tls", "openssl", @@ -253,8 +253,8 @@ dependencies = [ "bytes", "fastrand", "hex", - "http", - "hyper", + "http 0.2.11", + "hyper 0.14.28", "ring", "time", "tokio", @@ -284,8 +284,8 @@ dependencies = [ "aws-smithy-types", "aws-types", "bytes", - "http", - "http-body", + "http 0.2.11", + "http-body 0.4.6", "pin-project-lite", "tracing", ] @@ -306,7 +306,7 @@ dependencies = [ "aws-smithy-types", "aws-types", "fastrand", - "http", + "http 0.2.11", "percent-encoding", "tracing", "uuid", @@ -329,7 +329,7 @@ dependencies = [ "aws-smithy-types", "aws-smithy-xml", "aws-types", - "http", + "http 0.2.11", "once_cell", "regex-lite", "tracing", @@ -356,8 +356,8 @@ dependencies = [ "aws-smithy-xml", "aws-types", "bytes", - "http", - "http-body", + "http 0.2.11", + "http-body 0.4.6", "once_cell", "percent-encoding", "regex-lite", @@ -382,7 +382,7 @@ dependencies = [ "aws-smithy-types", "aws-types", "bytes", - "http", + "http 0.2.11", "once_cell", "regex-lite", "tracing", @@ -405,7 +405,7 @@ dependencies = [ "aws-smithy-types", "aws-types", "bytes", - "http", + "http 0.2.11", "once_cell", "regex-lite", "tracing", @@ -429,7 +429,7 @@ dependencies = [ "aws-smithy-types", "aws-smithy-xml", "aws-types", - "http", + "http 0.2.11", "once_cell", "regex-lite", "tracing", @@ -451,7 +451,7 @@ dependencies = [ "form_urlencoded", "hex", "hmac", - "http", + "http 0.2.11", "once_cell", "p256", "percent-encoding", @@ -486,8 +486,8 @@ dependencies = [ "crc32c", "crc32fast", "hex", - "http", - "http-body", + "http 0.2.11", + "http-body 0.4.6", "md-5", "pin-project-lite", "sha1", @@ -518,8 +518,8 @@ dependencies = [ "bytes", "bytes-utils", "futures-core", - "http", - "http-body", + "http 0.2.11", + "http-body 0.4.6", "once_cell", "percent-encoding", "pin-project-lite", @@ -544,7 +544,7 @@ checksum = "aecec08d0fcded5316998e312154854b6ae2cc81bc6e4f022ea8a099177bf839" dependencies = [ "assert-json-diff 1.1.0", "aws-smithy-runtime-api", - "http", + "http 0.2.11", "pretty_assertions", "regex-lite", "roxmltree", @@ -575,10 +575,10 @@ dependencies = [ "aws-smithy-types", "bytes", "fastrand", - "h2", - "http", - "http-body", - "hyper", + "h2 0.3.22", + "http 0.2.11", + "http-body 0.4.6", + "hyper 0.14.28", "hyper-rustls", "once_cell", "pin-project-lite", @@ -600,7 +600,7 @@ dependencies = [ "aws-smithy-async", "aws-smithy-types", "bytes", - "http", + "http 0.2.11", "pin-project-lite", "tokio", "tracing", @@ -617,8 +617,8 @@ dependencies = [ "bytes", "bytes-utils", "futures-core", - "http", - "http-body", + "http 0.2.11", + "http-body 0.4.6", "itoa 1.0.10", "num-integer", "pin-project-lite", @@ -659,26 +659,26 @@ dependencies = [ "aws-smithy-async", "aws-smithy-runtime-api", "aws-smithy-types", - "http", + "http 0.2.11", "rustc_version", "tracing", ] [[package]] name = "axum" -version = "0.6.20" +version = "0.7.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3b829e4e32b91e643de6eafe82b1d90675f5874230191a4ffbc1b336dec4d6bf" +checksum = "d09dbe0e490df5da9d69b36dca48a76635288a82f92eca90024883a56202026d" dependencies = [ "async-trait", "axum-core", - "bitflags 1.3.2", "bytes", "futures-util", - "headers", - "http", - "http-body", - "hyper", + "http 1.0.0", + "http-body 1.0.0", + "http-body-util", + "hyper 1.1.0", + "hyper-util", "itoa 1.0.10", "matchit", "memchr", @@ -695,41 +695,47 @@ dependencies = [ "tower", "tower-layer", "tower-service", + "tracing", ] [[package]] name = "axum-core" -version = "0.3.4" +version = "0.4.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "759fa577a247914fd3f7f76d62972792636412fbfd634cd452f6a385a74d2d2c" +checksum = "e87c8503f93e6d144ee5690907ba22db7ba79ab001a932ab99034f0fe836b3df" dependencies = [ "async-trait", "bytes", "futures-util", - "http", - "http-body", + "http 1.0.0", + "http-body 1.0.0", + "http-body-util", "mime", + "pin-project-lite", "rustversion", + "sync_wrapper", "tower-layer", "tower-service", + "tracing", ] [[package]] name = "axum-extra" -version = "0.8.0" +version = "0.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4ab90e7b70bea63a153137162affb6a0bce26b584c24a4c7885509783e2cf30b" +checksum = "881348a37b079994894b6e5e46edcc4b8a60e1c0333669a65b810abeed780598" dependencies = [ "axum", "axum-core", "bytes", "futures-util", - "http", - "http-body", + "headers", + "http 1.0.0", + "http-body 1.0.0", + "http-body-util", "mime", "pin-project-lite", "serde", - "tokio", "tower", "tower-layer", "tower-service", @@ -1551,9 +1557,10 @@ dependencies = [ "grass", "hex", "hostname", - "http", + "http 0.2.11", + "http 1.0.0", "humantime", - "hyper", + "hyper 1.1.0", "indoc", "itertools 0.12.0", "kuchikiki", @@ -2902,7 +2909,26 @@ dependencies = [ "futures-core", "futures-sink", "futures-util", - "http", + "http 0.2.11", + "indexmap 2.1.0", + "slab", + "tokio", + "tokio-util", + "tracing", +] + +[[package]] +name = "h2" +version = "0.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e1d308f63daf4181410c242d34c11f928dcb3aa105852019e043c9d1f4e4368a" +dependencies = [ + "bytes", + "fnv", + "futures-core", + "futures-sink", + "futures-util", + "http 1.0.0", "indexmap 2.1.0", "slab", "tokio", @@ -2961,14 +2987,14 @@ dependencies = [ [[package]] name = "headers" -version = "0.3.9" +version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "06683b93020a07e3dbcf5f8c0f6d40080d725bea7936fc01ad345c01b97dc270" +checksum = "322106e6bd0cba2d5ead589ddb8150a13d7c4217cf80d7c4f682ca994ccc6aa9" dependencies = [ "base64 0.21.5", "bytes", "headers-core", - "http", + "http 1.0.0", "httpdate", "mime", "sha1", @@ -2976,11 +3002,11 @@ dependencies = [ [[package]] name = "headers-core" -version = "0.2.0" +version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e7f66481bfee273957b1f20485a4ff3362987f85b2c236580d81b4eb7a326429" +checksum = "54b4a22553d4242c49fddb9ba998a99962b5cc6f22cb5a3482bec22522403ce4" dependencies = [ - "http", + "http 1.0.0", ] [[package]] @@ -3070,6 +3096,17 @@ dependencies = [ "itoa 1.0.10", ] +[[package]] +name = "http" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b32afd38673a8016f7c9ae69e5af41a58f81b1d31689040f2f1959594ce194ea" +dependencies = [ + "bytes", + "fnv", + "itoa 1.0.10", +] + [[package]] name = "http-body" version = "0.4.6" @@ -3077,15 +3114,38 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7ceab25649e9960c0311ea418d17bee82c0dcec1bd053b5f9a66e265a693bed2" dependencies = [ "bytes", - "http", + "http 0.2.11", + "pin-project-lite", +] + +[[package]] +name = "http-body" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1cac85db508abc24a2e48553ba12a996e87244a0395ce011e62b37158745d643" +dependencies = [ + "bytes", + "http 1.0.0", +] + +[[package]] +name = "http-body-util" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "41cb79eb393015dadd30fc252023adb0b2400a0caee0fa2a077e6e21a551e840" +dependencies = [ + "bytes", + "futures-util", + "http 1.0.0", + "http-body 1.0.0", "pin-project-lite", ] [[package]] name = "http-range-header" -version = "0.3.1" +version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "add0ab9360ddbd88cfeb3bd9574a1d85cfdfa14db10b3e21d3700dbc4328758f" +checksum = "3ce4ef31cda248bbdb6e6820603b82dfcd9e833db65a43e997a0ccec777d11fe" [[package]] name = "httparse" @@ -3124,9 +3184,9 @@ dependencies = [ "futures-channel", "futures-core", "futures-util", - "h2", - "http", - "http-body", + "h2 0.3.22", + "http 0.2.11", + "http-body 0.4.6", "httparse", "httpdate", "itoa 1.0.10", @@ -3138,6 +3198,25 @@ dependencies = [ "want", ] +[[package]] +name = "hyper" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb5aa53871fc917b1a9ed87b683a5d86db645e23acb32c2e0785a353e522fb75" +dependencies = [ + "bytes", + "futures-channel", + "futures-util", + "h2 0.4.0", + "http 1.0.0", + "http-body 1.0.0", + "httparse", + "httpdate", + "itoa 1.0.10", + "pin-project-lite", + "tokio", +] + [[package]] name = "hyper-rustls" version = "0.24.2" @@ -3145,8 +3224,8 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ec3efd23720e2049821a693cbc7e65ea87c72f1c58ff2f9522ff332b1491e590" dependencies = [ "futures-util", - "http", - "hyper", + "http 0.2.11", + "hyper 0.14.28", "log", "rustls", "rustls-native-certs", @@ -3161,12 +3240,30 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d6183ddfa99b85da61a140bea0efc93fdf56ceaa041b37d553518030827f9905" dependencies = [ "bytes", - "hyper", + "hyper 0.14.28", "native-tls", "tokio", "tokio-native-tls", ] +[[package]] +name = "hyper-util" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bdea9aac0dbe5a9240d68cfd9501e2db94222c6dc06843e06640b9e07f0fdc67" +dependencies = [ + "bytes", + "futures-channel", + "futures-util", + "http 1.0.0", + "http-body 1.0.0", + "hyper 1.1.0", + "pin-project-lite", + "socket2 0.5.5", + "tokio", + "tracing", +] + [[package]] name = "iana-time-zone" version = "0.1.59" @@ -3660,7 +3757,7 @@ dependencies = [ "assert-json-diff 2.0.2", "colored", "futures", - "hyper", + "hyper 0.14.28", "log", "rand 0.8.5", "regex", @@ -4665,10 +4762,10 @@ dependencies = [ "encoding_rs", "futures-core", "futures-util", - "h2", - "http", - "http-body", - "hyper", + "h2 0.3.22", + "http 0.2.11", + "http-body 0.4.6", + "hyper 0.14.28", "hyper-tls", "ipnet", "js-sys", @@ -4872,7 +4969,7 @@ dependencies = [ "futures-util", "getrandom 0.2.11", "git2", - "http", + "http 0.2.11", "lazy_static", "log", "nix 0.25.1", @@ -5014,9 +5111,9 @@ dependencies = [ [[package]] name = "sentry" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6ce4b57f1b521f674df7a1d200be8ff5d74e3712020ee25b553146657b5377d5" +checksum = "ab18211f62fb890f27c9bb04861f76e4be35e4c2fcbfc2d98afa37aadebb16f1" dependencies = [ "httpdate", "native-tls", @@ -5033,9 +5130,9 @@ dependencies = [ [[package]] name = "sentry-anyhow" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8868ca6e513f7a80b394b7e0f4b6071afeebb69e62b5e4aafe37b45e431fac8b" +checksum = "8041d88e52dce0fa26bf0bf5ae44f72053f74c2f04a46bf2115bc0d023b10075" dependencies = [ "anyhow", "sentry-backtrace", @@ -5044,9 +5141,9 @@ dependencies = [ [[package]] name = "sentry-backtrace" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "58cc8d4e04a73de8f718dc703943666d03f25d3e9e4d0fb271ca0b8c76dfa00e" +checksum = "cf018ff7d5ce5b23165a9cbfee60b270a55ae219bc9eebef2a3b6039356dd7e5" dependencies = [ "backtrace", "once_cell", @@ -5056,9 +5153,9 @@ dependencies = [ [[package]] name = "sentry-contexts" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6436c1bad22cdeb02179ea8ef116ffc217797c028927def303bc593d9320c0d1" +checksum = "1d934df6f9a17b8c15b829860d9d6d39e78126b5b970b365ccbd817bc0fe82c9" dependencies = [ "hostname", "libc", @@ -5070,9 +5167,9 @@ dependencies = [ [[package]] name = "sentry-core" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "901f761681f97db3db836ef9e094acdd8756c40215326c194201941947164ef1" +checksum = "5e362d3fb1c5de5124bf1681086eaca7adf6a8c4283a7e1545359c729f9128ff" dependencies = [ "once_cell", "rand 0.8.5", @@ -5083,9 +5180,9 @@ dependencies = [ [[package]] name = "sentry-debug-images" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "afdb263e73d22f39946f6022ed455b7561b22ff5553aca9be3c6a047fa39c328" +checksum = "d8bca420d75d9e7a8e54a4806bf4fa8a7e9a804e8f2ff05c7c80234168c6ca66" dependencies = [ "findshlibs", "once_cell", @@ -5094,9 +5191,9 @@ dependencies = [ [[package]] name = "sentry-panic" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "74fbf1c163f8b6a9d05912e1b272afa27c652e8b47ea60cb9a57ad5e481eea99" +checksum = "e0224e7a8e2bd8a32d96804acb8243d6d6e073fed55618afbdabae8249a964d8" dependencies = [ "sentry-backtrace", "sentry-core", @@ -5104,11 +5201,11 @@ dependencies = [ [[package]] name = "sentry-tower" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "88e782e369edac4adfc5bf528b27577270bc3e7023c388ebad9db08e1d56b30b" +checksum = "ca654f9bb134581169b51f2dcf713ae0909157121870a0b94e369368f75ab050" dependencies = [ - "http", + "http 1.0.0", "pin-project", "sentry-core", "tower-layer", @@ -5118,9 +5215,9 @@ dependencies = [ [[package]] name = "sentry-tracing" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "82eabcab0a047040befd44599a1da73d3adb228ff53b5ed9795ae04535577704" +checksum = "087bed8c616d176a9c6b662a8155e5f23b40dc9e1fa96d0bd5fb56e8636a9275" dependencies = [ "sentry-backtrace", "sentry-core", @@ -5130,9 +5227,9 @@ dependencies = [ [[package]] name = "sentry-types" -version = "0.31.8" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "da956cca56e0101998c8688bc65ce1a96f00673a0e58e663664023d4c7911e82" +checksum = "fb4f0e37945b7a8ce7faebc310af92442e2d7c5aa7ef5b42fe6daa98ee133f65" dependencies = [ "debugid", "hex", @@ -6132,16 +6229,16 @@ dependencies = [ [[package]] name = "tower-http" -version = "0.4.4" +version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "61c5bb1d698276a2443e5ecfabc1008bf15a36c12e6a7176e7bf089ea9131140" +checksum = "09e12e6351354851911bdf8c2b8f2ab15050c567d70a8b9a37ae7b8301a4080d" dependencies = [ "bitflags 2.4.1", "bytes", - "futures-core", "futures-util", - "http", - "http-body", + "http 1.0.0", + "http-body 1.0.0", + "http-body-util", "http-range-header", "httpdate", "mime", diff --git a/Cargo.toml b/Cargo.toml index d33200a33..fd0cc2a44 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -20,11 +20,11 @@ exclude = [ consistency_check = ["crates-index", "itertools"] [dependencies] -sentry = "0.31.0" -sentry-panic = "0.31.0" -sentry-tracing = "0.31.0" -sentry-tower = { version = "0.31.0", features = ["http"] } -sentry-anyhow = { version = "0.31.0", features = ["backtrace"] } +sentry = "0.32.1" +sentry-panic = "0.32.1" +sentry-tracing = "0.32.1" +sentry-tower = { version = "0.32.1", features = ["http"] } +sentry-anyhow = { version = "0.32.1", features = ["backtrace"] } log = "0.4" tracing = "0.1.37" tracing-subscriber = { version = "0.3.16", default-features = false, features = ["ansi", "fmt", "env-filter", "tracing-log"] } @@ -78,7 +78,7 @@ aws-config = "1.0.0" aws-sdk-s3 = "1.3.0" aws-sdk-cloudfront = "1.3.0" aws-smithy-types-convert = { version = "0.60.0", features = ["convert-chrono"] } -http = "0.2.6" +http = "1.0.0" uuid = { version = "1.1.2", features = ["v4"]} # Data serialization and deserialization @@ -86,12 +86,12 @@ serde = { version = "1.0", features = ["derive"] } serde_json = "1.0" # axum dependencies -axum = { version = "0.6.1", features = ["headers"]} -axum-extra = "0.8.0" -hyper = { version = "0.14.15", default-features = false } +axum = "0.7.3" +axum-extra = { version = "0.9.1", features = ["typed-header"] } +hyper = { version = "1.1.0", default-features = false } tower = "0.4.11" tower-service = "0.3.2" -tower-http = { version = "0.4.0", features = ["fs", "trace", "timeout", "catch-panic"] } +tower-http = { version = "0.5.0", features = ["fs", "trace", "timeout", "catch-panic"] } mime = "0.3.16" percent-encoding = "2.2.0" @@ -120,6 +120,7 @@ procfs = "0.15.1" [dev-dependencies] criterion = "0.5.1" kuchikiki = "0.8" +http02 = { version = "0.2.11", package = "http"} rand = "0.8" mockito = "1.0.2" test-case = "3.0.0" diff --git a/src/cdn.rs b/src/cdn.rs index 7a12d41d7..472365583 100644 --- a/src/cdn.rs +++ b/src/cdn.rs @@ -959,16 +959,16 @@ mod tests { #[tokio::test] async fn invalidate_path() { let conn = StaticReplayClient::new(vec![ReplayEvent::new( - http::Request::builder() + http02::Request::builder() .header("content-type", "application/xml") - .uri(http::uri::Uri::from_static( + .uri(http02::uri::Uri::from_static( "https://cloudfront.amazonaws.com/2020-05-31/distribution/some_distribution/invalidation", )) .body(SdkBody::from( r#"2/some/path*/another/path/*some_reference"#, )) .unwrap(), - http::Response::builder() + http02::Response::builder() .status(200) .body(SdkBody::from( r#" @@ -1009,14 +1009,14 @@ mod tests { #[tokio::test] async fn get_invalidation_info_doesnt_exist() { let conn = StaticReplayClient::new(vec![ReplayEvent::new( - http::Request::builder() + http02::Request::builder() .header("content-type", "application/xml") - .uri(http::uri::Uri::from_static( + .uri(http02::uri::Uri::from_static( "https://cloudfront.amazonaws.com/2020-05-31/distribution/some_distribution/invalidation/some_reference" )) .body(SdkBody::empty()) .unwrap(), - http::Response::builder() + http02::Response::builder() .status(404) .body(SdkBody::empty()) .unwrap(), @@ -1036,14 +1036,14 @@ mod tests { #[tokio::test] async fn get_invalidation_info_completed() { let conn = StaticReplayClient::new(vec![ReplayEvent::new( - http::Request::builder() + http02::Request::builder() .header("content-type", "application/xml") - .uri(http::uri::Uri::from_static( + .uri(http02::uri::Uri::from_static( "https://cloudfront.amazonaws.com/2020-05-31/distribution/some_distribution/invalidation/some_reference" )) .body(SdkBody::empty()) .unwrap(), - http::Response::builder() + http02::Response::builder() .status(200) .body(SdkBody::from( r#" diff --git a/src/test/mod.rs b/src/test/mod.rs index 16ca68d13..4490643e0 100644 --- a/src/test/mod.rs +++ b/src/test/mod.rs @@ -20,14 +20,7 @@ use reqwest::{ use sqlx::Connection as _; use std::thread::{self, JoinHandle}; use std::{ - fs, - future::Future, - net::{SocketAddr, TcpListener}, - panic, - rc::Rc, - str::FromStr, - sync::Arc, - time::Duration, + fs, future::Future, net::SocketAddr, panic, rc::Rc, str::FromStr, sync::Arc, time::Duration, }; use tokio::runtime::{Builder, Runtime}; use tokio::sync::oneshot::Sender; @@ -95,8 +88,10 @@ pub(crate) fn assert_no_cache(res: &Response) { assert_eq!( res.headers() .get("Cache-Control") - .expect("missing cache-control header"), - cache::NO_CACHING, + .expect("missing cache-control header") + .to_str() + .unwrap(), + cache::NO_CACHING.to_str().unwrap(), ); } @@ -111,8 +106,11 @@ pub(crate) fn assert_cache_control( if let Some(expected_directives) = cache_policy.render(config) { assert_eq!( - cache_control.expect("missing cache-control header"), - expected_directives, + cache_control + .expect("missing cache-control header") + .to_str() + .unwrap(), + expected_directives.to_str().unwrap(), ); } else { assert!(cache_control.is_none()); @@ -707,9 +705,14 @@ impl TestFrontend { debug!("loading template data"); let template_data = Arc::new(TemplateData::new(1).unwrap()); + let runtime = context.runtime().unwrap(); + debug!("binding local TCP port for axum"); - let axum_listener = - TcpListener::bind("127.0.0.1:0".parse::().unwrap()).unwrap(); + let axum_listener = runtime + .block_on(tokio::net::TcpListener::bind( + "127.0.0.1:0".parse::().unwrap(), + )) + .unwrap(); let axum_addr = axum_listener.local_addr().unwrap(); debug!("bound to local address: {}", axum_addr); @@ -723,9 +726,7 @@ impl TestFrontend { let runtime = context.runtime().unwrap(); move || { runtime.block_on(async { - axum::Server::from_tcp(axum_listener) - .unwrap() - .serve(axum_app.into_make_service()) + axum::serve(axum_listener, axum_app.into_make_service()) .with_graceful_shutdown(async { rx.await.ok(); }) diff --git a/src/web/cache.rs b/src/web/cache.rs index b9b5a40a1..b25b2fd58 100644 --- a/src/web/cache.rs +++ b/src/web/cache.rs @@ -1,6 +1,6 @@ use crate::config::Config; use axum::{ - http::Request as AxumHttpRequest, middleware::Next, response::Response as AxumResponse, + extract::Request as AxumHttpRequest, middleware::Next, response::Response as AxumResponse, }; use http::{header::CACHE_CONTROL, HeaderValue}; use std::sync::Arc; @@ -14,7 +14,7 @@ pub static NO_STORE_MUST_REVALIDATE: HeaderValue = pub static FOREVER_IN_CDN_AND_BROWSER: HeaderValue = HeaderValue::from_static("max-age=31104000"); /// defines the wanted caching behaviour for a web response. -#[derive(Debug)] +#[derive(Debug, Clone)] pub enum CachePolicy { /// no browser or CDN caching. /// In some cases the browser might still use cached content, @@ -79,7 +79,7 @@ impl CachePolicy { } } -pub(crate) async fn cache_middleware(req: AxumHttpRequest, next: Next) -> AxumResponse { +pub(crate) async fn cache_middleware(req: AxumHttpRequest, next: Next) -> AxumResponse { let config = req .extensions() .get::>() diff --git a/src/web/csp.rs b/src/web/csp.rs index edfb19d9d..44608df4a 100644 --- a/src/web/csp.rs +++ b/src/web/csp.rs @@ -1,6 +1,6 @@ use crate::config::Config; use axum::{ - http::Request as AxumHttpRequest, middleware::Next, response::Response as AxumResponse, + extract::Request as AxumHttpRequest, middleware::Next, response::Response as AxumResponse, }; use base64::{engine::general_purpose::STANDARD as b64, Engine}; use std::{ @@ -98,7 +98,7 @@ enum ContentType { Other, } -pub(crate) async fn csp_middleware(mut req: AxumHttpRequest, next: Next) -> AxumResponse { +pub(crate) async fn csp_middleware(mut req: AxumHttpRequest, next: Next) -> AxumResponse { let csp_report_only = req .extensions() .get::>() diff --git a/src/web/headers.rs b/src/web/headers.rs index 4c0ca44ba..b93a92257 100644 --- a/src/web/headers.rs +++ b/src/web/headers.rs @@ -1,9 +1,7 @@ use super::encode_url_path; use anyhow::Result; -use axum::{ - headers::{Header, HeaderName, HeaderValue}, - http::uri::{PathAndQuery, Uri}, -}; +use axum::http::uri::{PathAndQuery, Uri}; +use axum_extra::headers::{Header, HeaderName, HeaderValue}; use serde::Serialize; /// simplified typed header for a `Link rel=canonical` header in the response. @@ -35,7 +33,7 @@ impl Header for CanonicalUrl { &http::header::LINK } - fn decode<'i, I>(_values: &mut I) -> Result + fn decode<'i, I>(_values: &mut I) -> Result where I: Iterator, { @@ -67,8 +65,8 @@ impl Serialize for CanonicalUrl { mod tests { use super::*; - use axum::headers::HeaderMapExt; use axum::http::HeaderMap; + use axum_extra::headers::HeaderMapExt; #[test] fn test_serialize_canonical() { diff --git a/src/web/metrics.rs b/src/web/metrics.rs index 8f7b24364..2b1bd3b76 100644 --- a/src/web/metrics.rs +++ b/src/web/metrics.rs @@ -4,8 +4,7 @@ use crate::{ }; use anyhow::{Context as _, Result}; use axum::{ - extract::{Extension, MatchedPath}, - http::Request as AxumRequest, + extract::{Extension, MatchedPath, Request as AxumRequest}, http::{header::CONTENT_TYPE, StatusCode}, middleware::Next, response::IntoResponse, @@ -78,9 +77,9 @@ pub(super) async fn instance_metrics_handler( /// request_recorder(request, next, Some("static resource")).await /// })) /// ``` -pub(crate) async fn request_recorder( - request: AxumRequest, - next: Next, +pub(crate) async fn request_recorder( + request: AxumRequest, + next: Next, route_name: Option<&str>, ) -> impl IntoResponse { let route_name = if let Some(rn) = route_name { diff --git a/src/web/mod.rs b/src/web/mod.rs index 86c099a52..78647e7c9 100644 --- a/src/web/mod.rs +++ b/src/web/mod.rs @@ -33,8 +33,7 @@ mod status; use crate::{impl_axum_webpage, Context}; use anyhow::Error; use axum::{ - extract::Extension, - http::Request as AxumRequest, + extract::{Extension, Request as AxumRequest}, http::StatusCode, middleware, middleware::Next, @@ -234,7 +233,7 @@ async fn match_version( Err(AxumNope::VersionNotFound) } -async fn log_timeouts_to_sentry(req: AxumRequest, next: Next) -> AxumResponse { +async fn log_timeouts_to_sentry(req: AxumRequest, next: Next) -> AxumResponse { let uri = req.uri().clone(); let response = next.run(req).await; @@ -309,13 +308,22 @@ pub fn start_background_metrics_webserver( let runtime = context.runtime()?; runtime.spawn(async move { - if let Err(err) = axum::Server::bind(&axum_addr) - .serve(metrics_axum_app) + match tokio::net::TcpListener::bind(axum_addr) .await - .context("error running metrics web server") + .context("error binding socket for metrics web server") { - report_error(&err); - } + Ok(listener) => { + if let Err(err) = axum::serve(listener, metrics_axum_app) + .await + .context("error running metrics web server") + { + report_error(&err); + } + } + Err(err) => { + report_error(&err); + } + }; }); Ok(()) @@ -341,8 +349,11 @@ pub fn start_web_server(addr: Option, context: &dyn Context) -> Resu let app = build_axum_app(context, template_data)?.into_make_service(); context.runtime()?.block_on(async { - axum::Server::bind(&axum_addr) - .serve(app) + let listener = tokio::net::TcpListener::bind(axum_addr) + .await + .context("error binding socket for metrics web server")?; + + axum::serve(listener, app) .with_graceful_shutdown(shutdown_signal()) .await?; Ok::<(), Error>(()) @@ -744,7 +755,7 @@ mod test { .unwrap(); let web = env.frontend(); let response = web.get("/bat//").send()?; - assert_eq!(response.status(), StatusCode::NOT_FOUND); + assert_eq!(response.status().as_u16(), StatusCode::NOT_FOUND.as_u16()); Ok(()) }) } diff --git a/src/web/page/web_page.rs b/src/web/page/web_page.rs index b92fffc76..7ead62b42 100644 --- a/src/web/page/web_page.rs +++ b/src/web/page/web_page.rs @@ -2,8 +2,8 @@ use super::TemplateData; use crate::web::{csp::Csp, error::AxumNope}; use anyhow::Error; use axum::{ - body::{boxed, Body}, - http::Request as AxumRequest, + body::Body, + extract::Request as AxumRequest, middleware::Next, response::{IntoResponse, Response as AxumResponse}, }; @@ -68,7 +68,7 @@ macro_rules! impl_axum_webpage { )? // this empty body will be replaced in `render_templates_middleware` using // the data from `DelayedTemplateRender` below. - .body(::axum::body::boxed(::axum::body::Body::empty())) + .body(::axum::body::Body::empty()) .unwrap(); $( @@ -84,7 +84,7 @@ macro_rules! impl_axum_webpage { (canonical_url)(&self) }; if let Some(canonical_url) = canonical_url { - use axum::headers::HeaderMapExt; + use axum_extra::headers::HeaderMapExt; response.headers_mut().typed_insert(canonical_url); } @@ -113,6 +113,7 @@ macro_rules! impl_axum_webpage { /// adding this to the axum response extensions will lead /// to the template being rendered, adding the csp_nonce to /// the context. +#[derive(Clone)] pub(crate) struct DelayedTemplateRender { pub template: String, pub context: Context, @@ -166,7 +167,7 @@ fn render_response( } }; let content_length = rendered.len(); - *response.body_mut() = boxed(Body::from(rendered)); + *response.body_mut() = Body::from(rendered); response .headers_mut() .insert(CONTENT_LENGTH, content_length.into()); @@ -178,10 +179,7 @@ fn render_response( .boxed() } -pub(crate) async fn render_templates_middleware( - req: AxumRequest, - next: Next, -) -> AxumResponse { +pub(crate) async fn render_templates_middleware(req: AxumRequest, next: Next) -> AxumResponse { let templates: Arc = req .extensions() .get::>() diff --git a/src/web/routes.rs b/src/web/routes.rs index 024d7ffd6..f0630bf33 100644 --- a/src/web/routes.rs +++ b/src/web/routes.rs @@ -2,12 +2,11 @@ use super::{ cache::CachePolicy, error::AxumNope, metrics::request_recorder, statics::build_static_router, }; use axum::{ + extract::Request as AxumHttpRequest, handler::Handler as AxumHandler, - http::Request as AxumHttpRequest, middleware::{self, Next}, response::{IntoResponse, Redirect}, - routing::get, - routing::MethodRouter, + routing::{get, MethodRouter}, Router as AxumRouter, }; use axum_extra::routing::RouterExt; @@ -17,10 +16,9 @@ use tracing::{debug, instrument}; const INTERNAL_PREFIXES: &[&str] = &["-", "about", "crate", "releases", "sitemap.xml"]; #[instrument(skip_all)] -pub(crate) fn get_static(handler: H) -> MethodRouter +pub(crate) fn get_static(handler: H) -> MethodRouter where - H: AxumHandler, - B: Send + 'static + hyper::body::HttpBody, + H: AxumHandler, T: 'static, S: Clone + Send + Sync + 'static, { @@ -30,10 +28,9 @@ where } #[instrument(skip_all)] -fn get_internal(handler: H) -> MethodRouter +fn get_internal(handler: H) -> MethodRouter where - H: AxumHandler, - B: Send + 'static + hyper::body::HttpBody, + H: AxumHandler, T: 'static, S: Clone + Send + Sync + 'static, { @@ -43,10 +40,9 @@ where } #[instrument(skip_all)] -fn get_rustdoc(handler: H) -> MethodRouter +fn get_rustdoc(handler: H) -> MethodRouter where - H: AxumHandler, - B: Send + 'static + hyper::body::HttpBody, + H: AxumHandler, T: 'static, S: Clone + Send + Sync + 'static, { @@ -57,9 +53,9 @@ where .layer(middleware::from_fn(block_blacklisted_prefixes_middleware)) } -async fn block_blacklisted_prefixes_middleware( - request: AxumHttpRequest, - next: Next, +async fn block_blacklisted_prefixes_middleware( + request: AxumHttpRequest, + next: Next, ) -> impl IntoResponse { if let Some(first_component) = request.uri().path().trim_matches('/').split('/').next() { if !first_component.is_empty() diff --git a/src/web/source.rs b/src/web/source.rs index 1ccbffc5f..5dfc81930 100644 --- a/src/web/source.rs +++ b/src/web/source.rs @@ -11,7 +11,8 @@ use crate::{ AsyncStorage, }; use anyhow::{Context as _, Result}; -use axum::{extract::Path, headers::HeaderMapExt, response::IntoResponse, Extension}; +use axum::{extract::Path, response::IntoResponse, Extension}; +use axum_extra::headers::HeaderMapExt; use serde::{Deserialize, Serialize}; use std::{cmp::Ordering, sync::Arc}; use tracing::instrument; diff --git a/src/web/statics.rs b/src/web/statics.rs index d05c9d4a5..3f23888f8 100644 --- a/src/web/statics.rs +++ b/src/web/statics.rs @@ -1,14 +1,14 @@ use super::{cache::CachePolicy, metrics::request_recorder, routes::get_static}; use axum::{ - extract::Extension, - headers::HeaderValue, - http::{header::CONTENT_TYPE, Request}, + extract::{Extension, Request}, + http::header::CONTENT_TYPE, middleware, middleware::Next, response::{IntoResponse, Response}, routing::get_service, Router as AxumRouter, }; +use axum_extra::headers::HeaderValue; use tower_http::services::ServeDir; const VENDORED_CSS: &str = include_str!(concat!(env!("OUT_DIR"), "/vendored.css")); @@ -25,7 +25,7 @@ fn build_static_css_response(content: &'static str) -> impl IntoResponse { ) } -async fn set_needed_static_headers(req: Request, next: Next) -> Response { +async fn set_needed_static_headers(req: Request, next: Next) -> Response { let is_opensearch_xml = req.uri().path().ends_with("/opensearch.xml"); let mut response = next.run(req).await;