Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add trait_associated_type_default_removed lint #889

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
59 changes: 59 additions & 0 deletions src/lints/trait_associated_type_default_removed.ron
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
SemverQuery(
id: "trait_associated_type_default_removed",
human_readable_name: "non-sealed trait removed the default value for an associated type",
description: "A non-sealed trait associated type lost its default value, which breaks downstream implementations of the trait",
required_update: Major,
lint_level: Deny,
reference_link: Some("https://doc.rust-lang.org/cargo/reference/semver.html#trait-item-signature"),
query: r#"
{
CrateDiff {
current {
item {
... on Trait {
visibility_limit @filter(op: "=", value: ["$public"])

importable_path {
path @output @tag
public_api @filter(op: "=", value: ["$true"])
}

associated_type {
associated_type: name @output @tag
has_default @filter(op: "!=", value: ["$true"]) @output

span_: span @optional {
filename @output
begin_line @output
}
}
}
}
}
baseline {
item {
... on Trait {
visibility_limit @filter(op: "=", value: ["$public"]) @output
sealed @filter(op: "!=", value: ["$true"])

importable_path {
path @filter(op: "=", value: ["%path"])
public_api @filter(op: "=", value: ["$true"])
}

associated_type {
name @filter(op: "=", value: ["%associated_type"])
has_default @filter(op: "=", value: ["$true"])
}
}
}
}
}
}"#,
arguments: {
"public": "public",
"true": true,
},
error_message: "A non-sealed trait associated type lost its default value, which breaks downstream implementations of the trait",
per_result_error_template: Some("trait type {{join \"::\" path}}::{{associated_type}} in file {{span_filename}}:{{span_begin_line}}"),
)
1 change: 1 addition & 0 deletions src/query.rs
Original file line number Diff line number Diff line change
Expand Up @@ -837,6 +837,7 @@ add_lints!(
trait_associated_const_default_removed,
trait_associated_const_now_doc_hidden,
trait_associated_type_added,
trait_associated_type_default_removed,
trait_associated_type_now_doc_hidden,
trait_default_impl_removed,
trait_method_missing,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
[package]
publish = false
name = "trait_associated_type_default_removed"
version = "0.1.0"
edition = "2021"

[dependencies]
27 changes: 27 additions & 0 deletions test_crates/trait_associated_type_default_removed/new/src/lib.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
#![feature(associated_type_defaults)]

mod sealed {
obi1kenobi marked this conversation as resolved.
Show resolved Hide resolved
pub(crate) trait Sealed {}
}

pub trait WillLoseDefault {
type Foo;
}

pub trait WillLoseDefaultSealed: sealed::Sealed {
type Foo;
}

pub trait Unchanged {
type Foo = bool;
}
pub trait UnchangedSealed: sealed::Sealed {
type Foo = bool;
}

pub trait UnchangedNoDefault {
type Foo;
}
pub trait UnchangedNoDefaultSealed: sealed::Sealed {
type Foo;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
[package]
publish = false
name = "trait_associated_type_default_removed"
version = "0.1.0"
edition = "2021"

[dependencies]
27 changes: 27 additions & 0 deletions test_crates/trait_associated_type_default_removed/old/src/lib.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
#![feature(associated_type_defaults)]

mod sealed {
obi1kenobi marked this conversation as resolved.
Show resolved Hide resolved
pub(crate) trait Sealed {}
}

pub trait WillLoseDefault {
type Foo = bool;
}

pub trait WillLoseDefaultSealed: sealed::Sealed {
type Foo = bool;
}

pub trait Unchanged {
type Foo = bool;
}
pub trait UnchangedSealed: sealed::Sealed {
type Foo = bool;
}

pub trait UnchangedNoDefault {
type Foo;
}
pub trait UnchangedNoDefaultSealed: sealed::Sealed {
type Foo;
}
15 changes: 15 additions & 0 deletions test_outputs/trait_associated_type_default_removed.output.ron
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
{
"./test_crates/trait_associated_type_default_removed/": [
{
"associated_type": String("Foo"),
"has_default": Boolean(false),
"path": List([
String("trait_associated_type_default_removed"),
String("WillLoseDefault"),
]),
"span_begin_line": Uint64(8),
"span_filename": String("src/lib.rs"),
"visibility_limit": String("public"),
},
],
}
Loading