diff --git a/Cargo.toml b/Cargo.toml index 28a8aad8..a22658e8 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -12,3 +12,18 @@ members = [ "contrib/ws/", "docs/tests", ] + +[workspace.lints.rust] +unexpected_cfgs = { level = "warn", check-cfg = ['cfg(nightly)'] } +rust_2018_idioms = "warn" +async_fn_in_trait = "allow" +refining_impl_trait = "allow" +# unreachable_pub = "warn" +# single_use_lifetimes = "warn" +# missing_docs = "warn" + +[workspace.lints.clippy] +type_complexity = "allow" +module_inception = "allow" +multiple_bound_locations = "allow" +manual_range_contains = "allow" diff --git a/contrib/db_pools/codegen/Cargo.toml b/contrib/db_pools/codegen/Cargo.toml index 42507ca0..aade9350 100644 --- a/contrib/db_pools/codegen/Cargo.toml +++ b/contrib/db_pools/codegen/Cargo.toml @@ -13,6 +13,9 @@ rust-version = "1.75" [lib] proc-macro = true +[lints] +workspace = true + [dependencies] devise = "0.4" quote = "1" diff --git a/contrib/db_pools/lib/Cargo.toml b/contrib/db_pools/lib/Cargo.toml index f2fbe7c4..7245ef0d 100644 --- a/contrib/db_pools/lib/Cargo.toml +++ b/contrib/db_pools/lib/Cargo.toml @@ -13,6 +13,9 @@ rust-version = "1.75" [package.metadata.docs.rs] all-features = true +[lints] +workspace = true + [features] # deadpool features deadpool_postgres = ["deadpool-postgres", "deadpool"] diff --git a/contrib/dyn_templates/Cargo.toml b/contrib/dyn_templates/Cargo.toml index c62bc4fb..1cd92099 100644 --- a/contrib/dyn_templates/Cargo.toml +++ b/contrib/dyn_templates/Cargo.toml @@ -12,9 +12,8 @@ license = "MIT OR Apache-2.0" edition = "2021" rust-version = "1.75" -[lints.clippy] -type_complexity = "allow" -multiple_bound_locations = "allow" +[lints] +workspace = true [features] tera = ["dep:tera"] diff --git a/contrib/sync_db_pools/codegen/Cargo.toml b/contrib/sync_db_pools/codegen/Cargo.toml index a099ea55..816cc45a 100644 --- a/contrib/sync_db_pools/codegen/Cargo.toml +++ b/contrib/sync_db_pools/codegen/Cargo.toml @@ -13,6 +13,9 @@ rust-version = "1.75" [lib] proc-macro = true +[lints] +workspace = true + [dependencies] quote = "1.0" devise = "0.4" diff --git a/contrib/sync_db_pools/lib/Cargo.toml b/contrib/sync_db_pools/lib/Cargo.toml index 0420e1c7..5d17119c 100644 --- a/contrib/sync_db_pools/lib/Cargo.toml +++ b/contrib/sync_db_pools/lib/Cargo.toml @@ -10,6 +10,9 @@ license = "MIT OR Apache-2.0" edition = "2021" rust-version = "1.75" +[lints] +workspace = true + [features] diesel_sqlite_pool = ["diesel/sqlite", "diesel/r2d2"] diesel_postgres_pool = ["diesel/postgres", "diesel/r2d2"] diff --git a/contrib/sync_db_pools/lib/tests/databases.rs b/contrib/sync_db_pools/lib/tests/databases.rs index 3219a481..ae72a6c2 100644 --- a/contrib/sync_db_pools/lib/tests/databases.rs +++ b/contrib/sync_db_pools/lib/tests/databases.rs @@ -11,8 +11,8 @@ mod databases_tests { struct PrimaryDb(diesel::PgConnection); } -#[cfg(all(feature = "databases", feature = "sqlite_pool"))] #[cfg(test)] +#[cfg(all(feature = "sqlite_pool"))] mod rusqlite_integration_test { use rocket_sync_db_pools::{rusqlite, database}; @@ -58,13 +58,13 @@ mod rusqlite_integration_test { } #[cfg(test)] -#[cfg(feature = "databases")] mod sentinel_and_runtime_test { use rocket::{Rocket, Build}; use r2d2::{ManageConnection, Pool}; use rocket_sync_db_pools::{database, Poolable, PoolResult}; use tokio::runtime::Runtime; + #[allow(dead_code)] struct ContainsRuntime(Runtime); struct TestConnection; diff --git a/contrib/ws/Cargo.toml b/contrib/ws/Cargo.toml index 00c0814f..417f28fc 100644 --- a/contrib/ws/Cargo.toml +++ b/contrib/ws/Cargo.toml @@ -12,6 +12,9 @@ license = "MIT OR Apache-2.0" edition = "2021" rust-version = "1.75" +[lints] +workspace = true + [features] default = ["tungstenite"] tungstenite = ["tokio-tungstenite"] diff --git a/core/codegen/Cargo.toml b/core/codegen/Cargo.toml index 5010690a..dd74e4ee 100644 --- a/core/codegen/Cargo.toml +++ b/core/codegen/Cargo.toml @@ -12,13 +12,12 @@ license = "MIT OR Apache-2.0" edition = "2021" rust-version = "1.75" +[lints] +workspace = true + [lib] proc-macro = true -[lints.clippy] -manual_range_contains = "allow" -large_enum_variant = "allow" - [dependencies] indexmap = "2" quote = "1.0" diff --git a/core/codegen/src/syn_ext.rs b/core/codegen/src/syn_ext.rs index 73ab6166..78adf5eb 100644 --- a/core/codegen/src/syn_ext.rs +++ b/core/codegen/src/syn_ext.rs @@ -187,7 +187,7 @@ impl TypeExt for syn::Type { fn is_concrete(&self, generics: &[&Ident]) -> bool { struct ConcreteVisitor<'i>(bool, &'i [&'i Ident]); - impl<'a, 'i> Visit<'a> for ConcreteVisitor<'i> { + impl<'a> Visit<'a> for ConcreteVisitor<'_> { fn visit_type(&mut self, ty: &'a syn::Type) { use syn::Type::*; diff --git a/core/codegen/tests/catcher.rs b/core/codegen/tests/catcher.rs index d3ecdd70..ddc59cb1 100644 --- a/core/codegen/tests/catcher.rs +++ b/core/codegen/tests/catcher.rs @@ -10,9 +10,9 @@ use rocket::local::blocking::Client; use rocket::http::Status; #[catch(404)] fn not_found_0() -> &'static str { "404-0" } -#[catch(404)] fn not_found_1(_: &Request) -> &'static str { "404-1" } -#[catch(404)] fn not_found_2(_: Status, _: &Request) -> &'static str { "404-2" } -#[catch(default)] fn all(_: Status, r: &Request) -> String { r.uri().to_string() } +#[catch(404)] fn not_found_1(_: &Request<'_>) -> &'static str { "404-1" } +#[catch(404)] fn not_found_2(_: Status, _: &Request<'_>) -> &'static str { "404-2" } +#[catch(default)] fn all(_: Status, r: &Request<'_>) -> String { r.uri().to_string() } #[test] fn test_simple_catchers() { @@ -37,10 +37,10 @@ fn test_simple_catchers() { } #[get("/")] fn forward(code: u16) -> Status { Status::new(code) } -#[catch(400)] fn forward_400(status: Status, _: &Request) -> String { status.code.to_string() } -#[catch(404)] fn forward_404(status: Status, _: &Request) -> String { status.code.to_string() } -#[catch(444)] fn forward_444(status: Status, _: &Request) -> String { status.code.to_string() } -#[catch(500)] fn forward_500(status: Status, _: &Request) -> String { status.code.to_string() } +#[catch(400)] fn forward_400(status: Status, _: &Request<'_>) -> String { status.code.to_string() } +#[catch(404)] fn forward_404(status: Status, _: &Request<'_>) -> String { status.code.to_string() } +#[catch(444)] fn forward_444(status: Status, _: &Request<'_>) -> String { status.code.to_string() } +#[catch(500)] fn forward_500(status: Status, _: &Request<'_>) -> String { status.code.to_string() } #[test] fn test_status_param() { diff --git a/core/codegen/tests/from_form.rs b/core/codegen/tests/from_form.rs index bed73596..0850e9dc 100644 --- a/core/codegen/tests/from_form.rs +++ b/core/codegen/tests/from_form.rs @@ -243,23 +243,23 @@ fn field_renaming() { } let form_string = &["single=123", "some_case=hi_im_here"].join("&"); - let form: Option = strict(&form_string).ok(); + let form: Option> = strict(&form_string).ok(); assert_eq!(form, Some(MultiName { single: 123, some_case: "hi_im_here", })); let form_string = &["single=123", "SomeCase=HiImHere"].join("&"); - let form: Option = strict(&form_string).ok(); + let form: Option> = strict(&form_string).ok(); assert_eq!(form, Some(MultiName { single: 123, some_case: "HiImHere", })); let form_string = &["single=123", "some_case=hi_im_here", "SomeCase=HiImHere"].join("&"); - let form: Option = strict(&form_string).ok(); + let form: Option> = strict(&form_string).ok(); assert!(form.is_none()); let form_string = &["single=123", "some_case=hi_im_here", "SomeCase=HiImHere"].join("&"); - let form: Option = lenient(&form_string).ok(); + let form: Option> = lenient(&form_string).ok(); assert_eq!(form, Some(MultiName { single: 123, some_case: "hi_im_here", })); let form_string = &["single=123", "SomeCase=HiImHere", "some_case=hi_im_here"].join("&"); - let form: Option = lenient(&form_string).ok(); + let form: Option> = lenient(&form_string).ok(); assert_eq!(form, Some(MultiName { single: 123, some_case: "HiImHere", })); #[derive(Debug, PartialEq, FromForm)] @@ -273,19 +273,19 @@ fn field_renaming() { } let form_string = &["HeLLO=123", "sOMECASe=hi_im_here"].join("&"); - let form: Option = strict(&form_string).ok(); + let form: Option> = strict(&form_string).ok(); assert_eq!(form, Some(CaseInsensitive { hello: 123, some_case: "hi_im_here", })); let form_string = &["hello=456", "SomeCase=HiImHere"].join("&"); - let form: Option = strict(&form_string).ok(); + let form: Option> = strict(&form_string).ok(); assert_eq!(form, Some(CaseInsensitive { hello: 456, some_case: "HiImHere", })); let form_string = &["helLO=789", "some_case=hi_there"].join("&"); - let form: Option = strict(&form_string).ok(); + let form: Option> = strict(&form_string).ok(); assert_eq!(form, Some(CaseInsensitive { hello: 789, some_case: "hi_there", })); let form_string = &["hello=123", "SOme_case=hi_im_here"].join("&"); - let form: Option = strict(&form_string).ok(); + let form: Option> = strict(&form_string).ok(); assert!(form.is_none()); } @@ -479,7 +479,7 @@ fn test_multi() { more_dogs: HashMap<&'r str, Dog>, } - let multi: Multi = strict("checks=true&checks=false&checks=false\ + let multi: Multi<'_> = strict("checks=true&checks=false&checks=false\ &names=Sam&names[]=Smith&names[]=Bob\ &news[]=Here&news[]=also here\ &dogs[fido].barks=true&dogs[George].barks=false\ @@ -545,17 +545,17 @@ struct Person<'r> { #[test] fn test_nested_multi() { - let person: Person = lenient("sitting.barks=true&sitting.trained=true").unwrap(); + let person: Person<'_> = lenient("sitting.barks=true&sitting.trained=true").unwrap(); assert_eq!(person, Person { sitting: Dog { barks: true, trained: true }, cats: vec![], dogs: vec![], }); - let person = strict::("sitting.barks=true&sitting.trained=true"); + let person = strict::>("sitting.barks=true&sitting.trained=true"); assert!(person.is_err()); - let person: Person = lenient("sitting.barks=true&sitting.trained=true\ + let person: Person<'_> = lenient("sitting.barks=true&sitting.trained=true\ &dogs[0].name=fido&dogs[0].pet.trained=yes&dogs[0].age=7&dogs[0].pet.barks=no\ ").unwrap(); assert_eq!(person, Person { @@ -568,11 +568,11 @@ fn test_nested_multi() { }] }); - let person = strict::("sitting.barks=true&sitting.trained=true\ + let person = strict::>("sitting.barks=true&sitting.trained=true\ &dogs[0].name=fido&dogs[0].pet.trained=yes&dogs[0].age=7&dogs[0].pet.barks=no"); assert!(person.is_err()); - let person: Person = lenient("sitting.trained=no&sitting.barks=true\ + let person: Person<'_> = lenient("sitting.trained=no&sitting.barks=true\ &dogs[0].name=fido&dogs[0].pet.trained=yes&dogs[0].age=7&dogs[0].pet.barks=no\ &dogs[1].pet.barks=true&dogs[1].name=Bob&dogs[1].pet.trained=no&dogs[1].age=1\ ").unwrap(); @@ -593,7 +593,7 @@ fn test_nested_multi() { ] }); - let person: Person = strict("sitting.barks=true&sitting.trained=no\ + let person: Person<'_> = strict("sitting.barks=true&sitting.trained=no\ &dogs[0].name=fido&dogs[0].pet.trained=yes&dogs[0].age=7&dogs[0].pet.barks=no\ &dogs[1].pet.barks=true&dogs[1].name=Bob&dogs[1].pet.trained=no&dogs[1].age=1\ &cats[george].pet.nip=paws&cats[george].name=George&cats[george].age=2\ @@ -636,7 +636,7 @@ fn test_multipart() { } #[rocket::post("/", data = "
")] - fn form(form: Form) { + fn form(form: Form>) { assert_eq!(form.names, &["abcd", "123"]); assert_eq!(form.file.name(), Some("foo")); } @@ -797,11 +797,11 @@ fn test_defaults() { } // `field2` has no default. - assert!(lenient::("").is_err()); + assert!(lenient::>("").is_err()); // every other field should. let form_string = &["field2=102"].join("&"); - let form1: Option = lenient(&form_string).ok(); + let form1: Option> = lenient(&form_string).ok(); assert_eq!(form1, Some(FormWithDefaults { field1: 100, field2: 102, @@ -834,12 +834,12 @@ fn test_defaults() { ), })); - let form2: Option = strict(&form_string).ok(); + let form2: Option> = strict(&form_string).ok(); assert!(form2.is_none()); // Ensure actual form field values take precedence. let form_string = &["field1=101", "field2=102", "field3=true", "field5=true"].join("&"); - let form3: Option = lenient(&form_string).ok(); + let form3: Option> = lenient(&form_string).ok(); assert_eq!(form3, Some(FormWithDefaults { field1: 101, field2: 102, @@ -852,7 +852,7 @@ fn test_defaults() { // And that strict parsing still works. let form = form3.unwrap(); let form_string = format!("{}", &form as &dyn UriDisplay); - let form4: form::Result<'_, FormWithDefaults> = strict(&form_string); + let form4: form::Result<'_, FormWithDefaults<'_>> = strict(&form_string); assert_eq!(form4, Ok(form), "parse from {}", form_string); #[derive(FromForm, UriDisplayQuery, PartialEq, Debug)] @@ -940,22 +940,22 @@ struct TokenOwned(String); #[test] fn wrapper_works() { - let form: Option = lenient("").ok(); + let form: Option> = lenient("").ok(); assert_eq!(form, Some(Token("some default hello"))); let form: Option = lenient("").ok(); assert_eq!(form, Some(TokenOwned("123456".into()))); - let errors = strict::("").unwrap_err(); + let errors = strict::>("").unwrap_err(); assert!(errors.iter().any(|e| matches!(e.kind, ErrorKind::Missing))); - let form: Option = lenient("=hi there").ok(); + let form: Option> = lenient("=hi there").ok(); assert_eq!(form, Some(Token("hi there"))); let form: Option = strict_encoded("=2318").ok(); assert_eq!(form, Some(TokenOwned("2318".into()))); - let errors = lenient::("=hi").unwrap_err(); + let errors = lenient::>("=hi").unwrap_err(); assert!(errors.iter().any(|e| matches!(e.kind, ErrorKind::InvalidLength { .. }))); let errors = lenient::("=hellothere").unwrap_err(); diff --git a/core/codegen/tests/responder.rs b/core/codegen/tests/responder.rs index d21d0872..35e2e7b2 100644 --- a/core/codegen/tests/responder.rs +++ b/core/codegen/tests/responder.rs @@ -127,19 +127,20 @@ async fn generic_responder() { let local_req = client.get("/"); let req = local_req.inner(); - let v: MyResult<_, (), ContentType, Cookie<'static>> = MyResult::Ok(Json("hi")); + let v: MyResult<'_, _, (), ContentType, Cookie<'static>> = MyResult::Ok(Json("hi")); let mut r = v.respond_to(req).unwrap(); assert_eq!(r.status(), Status::Ok); assert_eq!(r.content_type().unwrap(), ContentType::JSON); assert_eq!(r.body_mut().to_string().await.unwrap(), "\"hi\""); - let v: MyResult<(), &[u8], _, _> = MyResult::Err(&[7, 13, 23], ContentType::JPEG, Accept::Text); + let bytes = &[7, 13, 23]; + let v: MyResult<'_, (), &[u8], _, _> = MyResult::Err(bytes, ContentType::JPEG, Accept::Text); let mut r = v.respond_to(req).unwrap(); assert_eq!(r.status(), Status::NotFound); assert_eq!(r.content_type().unwrap(), ContentType::JPEG); - assert_eq!(r.body_mut().to_bytes().await.unwrap(), vec![7, 13, 23]); + assert_eq!(r.body_mut().to_bytes().await.unwrap(), bytes); - let v: MyResult<(), &[u8], ContentType, Accept> = MyResult::Other("beep beep"); + let v: MyResult<'_, (), &[u8], ContentType, Accept> = MyResult::Other("beep beep"); let mut r = v.respond_to(req).unwrap(); assert_eq!(r.status(), Status::InternalServerError); assert_eq!(r.content_type().unwrap(), ContentType::Text); diff --git a/core/codegen/tests/route-raw.rs b/core/codegen/tests/route-raw.rs index 22f608bd..9ce65167 100644 --- a/core/codegen/tests/route-raw.rs +++ b/core/codegen/tests/route-raw.rs @@ -15,7 +15,7 @@ fn swap(r#raw: String, bare: String) -> String { } #[catch(400)] -fn catch(r#raw: &rocket::Request) -> String { +fn catch(r#raw: &rocket::Request<'_>) -> String { format!("{}", raw.method()) } diff --git a/core/http/Cargo.toml b/core/http/Cargo.toml index bfdbcda2..ff62a0ae 100644 --- a/core/http/Cargo.toml +++ b/core/http/Cargo.toml @@ -15,16 +15,14 @@ categories = ["web-programming"] edition = "2021" rust-version = "1.75" +[lints] +workspace = true + [features] default = [] serde = ["dep:serde", "uncased/with-serde-alloc"] uuid = ["dep:uuid"] -[lints.clippy] -module_inception = "allow" -multiple_bound_locations = "allow" -manual_range_contains = "allow" - [dependencies] tinyvec = { version = "1.6", features = ["std", "rustc_1_57"] } percent-encoding = "2" diff --git a/core/lib/Cargo.toml b/core/lib/Cargo.toml index 1383006f..8fd3a301 100644 --- a/core/lib/Cargo.toml +++ b/core/lib/Cargo.toml @@ -19,17 +19,8 @@ rust-version = "1.75" [package.metadata.docs.rs] all-features = true -[lints.rust] -rust_2018_idioms = "warn" -# missing_docs = "warn" -async_fn_in_trait = "allow" -refining_impl_trait = "allow" - -[lints.clippy] -type_complexity = "allow" -module_inception = "allow" -multiple_bound_locations = "allow" -manual_range_contains = "allow" +[lints] +workspace = true [features] default = ["http2", "tokio-macros"] diff --git a/core/lib/fuzz/Cargo.toml b/core/lib/fuzz/Cargo.toml index eeae9d2d..ba42a712 100644 --- a/core/lib/fuzz/Cargo.toml +++ b/core/lib/fuzz/Cargo.toml @@ -8,6 +8,9 @@ edition = "2021" [package.metadata] cargo-fuzz = true +[lints.rust] +unexpected_cfgs = { level = "warn", check-cfg = ['cfg(honggfuzz)', 'cfg(afl)'] } + [dependencies] libfuzzer-sys = "0.4" arbitrary = { version = "1.3", features = ["derive"] } diff --git a/core/lib/fuzz/targets/collision-matching.rs b/core/lib/fuzz/targets/collision-matching.rs index 2af226ac..03675f31 100644 --- a/core/lib/fuzz/targets/collision-matching.rs +++ b/core/lib/fuzz/targets/collision-matching.rs @@ -204,7 +204,7 @@ fn fuzz((route_a, route_b, req): TestData<'_>) { #[cfg(all(not(honggfuzz), not(afl)))] libfuzzer_sys::fuzz_target!(|data: TestData| fuzz(data)); -#[cfg(honggbuzz)] +#[cfg(honggfuzz)] fn main() { loop { honggfuzz::fuzz!(|data: TestData| fuzz(data)); diff --git a/core/lib/tests/sentinel.rs b/core/lib/tests/sentinel.rs index b9181fa7..4221e3ac 100644 --- a/core/lib/tests/sentinel.rs +++ b/core/lib/tests/sentinel.rs @@ -321,7 +321,7 @@ async fn known_macro_sentinel_works() { } #[get("/<_a>/")] - fn reader<'a, 'b>(_a: &'a str, b: &'b str) -> ReaderStream![TextSentinel<'b>] { + fn reader<'b>(_a: &str, b: &'b str) -> ReaderStream![TextSentinel<'b>] { ReaderStream!(yield TextSentinel(b);) } diff --git a/docs/tests/Cargo.toml b/docs/tests/Cargo.toml index 9daf3bff..3e906e1c 100644 --- a/docs/tests/Cargo.toml +++ b/docs/tests/Cargo.toml @@ -5,6 +5,9 @@ workspace = "../../" edition = "2021" publish = false +[lints] +workspace = true + [dependencies] rocket = { path = "../../core/lib", features = ["secrets"] }