Skip to content

Commit

Permalink
Implement PGH003 - no blanket type ignore
Browse files Browse the repository at this point in the history
  • Loading branch information
squiddy committed Dec 17, 2022
1 parent 7ef6cd0 commit f213aff
Show file tree
Hide file tree
Showing 8 changed files with 86 additions and 5 deletions.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -899,6 +899,7 @@ For more, see [pygrep-hooks](https://github.com/pre-commit/pygrep-hooks) on GitH
| ---- | ---- | ------- | --- |
| PGH001 | NoEval | No builtin `eval()` allowed | |
| PGH002 | DeprecatedLogWarn | `warn` is deprecated in favor of `warning` | |
| PGH003 | BlanketTypeIgnore | Use specific error codes when ignoring type issues | |

### Pylint (PLC, PLE, PLR, PLW)

Expand Down
11 changes: 11 additions & 0 deletions resources/test/fixtures/pygrep-hooks/PGH003_0.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
x = 1 # type: ignore
x = 1 # type ignore
x = 1 # type:ignore

x = 1
x = 1 # type ignore # noqa
x = 1 # type: ignore[attr-defined]
x = 1 # type: ignore[attr-defined, name-defined]
x = 1 # type: ignore[type-mismatch] # noqa
x = 1 # type: Union[int, str]
x = 1 # type: ignoreme
8 changes: 8 additions & 0 deletions src/checkers/lines.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

use crate::checks::{Check, CheckCode};
use crate::pycodestyle::checks::{line_too_long, no_newline_at_end_of_file};
use crate::pygrep_hooks::plugins::blanket_type_ignore;
use crate::pyupgrade::checks::unnecessary_coding_comment;
use crate::settings::{flags, Settings};

Expand All @@ -11,6 +12,7 @@ pub fn check_lines(contents: &str, settings: &Settings, autofix: flags::Autofix)
let enforce_unnecessary_coding_comment = settings.enabled.contains(&CheckCode::UP009);
let enforce_line_too_long = settings.enabled.contains(&CheckCode::E501);
let enforce_no_newline_at_end_of_file = settings.enabled.contains(&CheckCode::W292);
let enforce_blanket_type_ignore = settings.enabled.contains(&CheckCode::PGH003);

for (lineno, line) in contents.lines().enumerate() {
// Enforce unnecessary coding comments (UP009).
Expand All @@ -33,6 +35,12 @@ pub fn check_lines(contents: &str, settings: &Settings, autofix: flags::Autofix)
checks.push(check);
}
}

if enforce_blanket_type_ignore {
if let Some(check) = blanket_type_ignore(lineno, line) {
checks.push(check);
}
}
}

// Enforce newlines at end of files (W292).
Expand Down
12 changes: 11 additions & 1 deletion src/checks.rs
Original file line number Diff line number Diff line change
Expand Up @@ -317,6 +317,7 @@ pub enum CheckCode {
// pygrep-hooks
PGH001,
PGH002,
PGH003,
// pandas-vet
PDV002,
PDV003,
Expand Down Expand Up @@ -889,6 +890,7 @@ pub enum CheckKind {
// pygrep-hooks
NoEval,
DeprecatedLogWarn,
BlanketTypeIgnore,
// flake8-unused-arguments
UnusedFunctionArgument(String),
UnusedMethodArgument(String),
Expand Down Expand Up @@ -927,7 +929,9 @@ impl CheckCode {
pub fn lint_source(&self) -> &'static LintSource {
match self {
CheckCode::RUF100 => &LintSource::NoQA,
CheckCode::E501 | CheckCode::W292 | CheckCode::UP009 => &LintSource::Lines,
CheckCode::E501 | CheckCode::W292 | CheckCode::UP009 | CheckCode::PGH003 => {
&LintSource::Lines
}
CheckCode::ERA001
| CheckCode::Q000
| CheckCode::Q001
Expand Down Expand Up @@ -1263,6 +1267,7 @@ impl CheckCode {
// pygrep-hooks
CheckCode::PGH001 => CheckKind::NoEval,
CheckCode::PGH002 => CheckKind::DeprecatedLogWarn,
CheckCode::PGH003 => CheckKind::BlanketTypeIgnore,
// flake8-unused-arguments
CheckCode::ARG001 => CheckKind::UnusedFunctionArgument("...".to_string()),
CheckCode::ARG002 => CheckKind::UnusedMethodArgument("...".to_string()),
Expand Down Expand Up @@ -1508,6 +1513,7 @@ impl CheckCode {
CheckCode::PDV901 => CheckCategory::PandasVet,
CheckCode::PGH001 => CheckCategory::PygrepHooks,
CheckCode::PGH002 => CheckCategory::PygrepHooks,
CheckCode::PGH003 => CheckCategory::PygrepHooks,
CheckCode::PLC0414 => CheckCategory::Pylint,
CheckCode::PLC2201 => CheckCategory::Pylint,
CheckCode::PLC3002 => CheckCategory::Pylint,
Expand Down Expand Up @@ -1852,6 +1858,7 @@ impl CheckKind {
// pygrep-hooks
CheckKind::NoEval => &CheckCode::PGH001,
CheckKind::DeprecatedLogWarn => &CheckCode::PGH002,
CheckKind::BlanketTypeIgnore => &CheckCode::PGH003,
// flake8-unused-arguments
CheckKind::UnusedFunctionArgument(..) => &CheckCode::ARG001,
CheckKind::UnusedMethodArgument(..) => &CheckCode::ARG002,
Expand Down Expand Up @@ -2692,6 +2699,9 @@ impl CheckKind {
CheckKind::DeprecatedLogWarn => {
"`warn` is deprecated in favor of `warning`".to_string()
}
CheckKind::BlanketTypeIgnore => {
"Use specific error codes when ignoring type issues".to_string()
}
// flake8-unused-arguments
CheckKind::UnusedFunctionArgument(name) => {
format!("Unused function argument: `{name}`")
Expand Down
9 changes: 6 additions & 3 deletions src/checks_gen.rs
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,7 @@ pub enum CheckCodePrefix {
PGH00,
PGH001,
PGH002,
PGH003,
PLC,
PLC0,
PLC04,
Expand Down Expand Up @@ -1425,11 +1426,12 @@ impl CheckCodePrefix {
CheckCodePrefix::PDV9 => vec![CheckCode::PDV901],
CheckCodePrefix::PDV90 => vec![CheckCode::PDV901],
CheckCodePrefix::PDV901 => vec![CheckCode::PDV901],
CheckCodePrefix::PGH => vec![CheckCode::PGH001, CheckCode::PGH002],
CheckCodePrefix::PGH0 => vec![CheckCode::PGH001, CheckCode::PGH002],
CheckCodePrefix::PGH00 => vec![CheckCode::PGH001, CheckCode::PGH002],
CheckCodePrefix::PGH => vec![CheckCode::PGH001, CheckCode::PGH002, CheckCode::PGH003],
CheckCodePrefix::PGH0 => vec![CheckCode::PGH001, CheckCode::PGH002, CheckCode::PGH003],
CheckCodePrefix::PGH00 => vec![CheckCode::PGH001, CheckCode::PGH002, CheckCode::PGH003],
CheckCodePrefix::PGH001 => vec![CheckCode::PGH001],
CheckCodePrefix::PGH002 => vec![CheckCode::PGH002],
CheckCodePrefix::PGH003 => vec![CheckCode::PGH003],
CheckCodePrefix::PLC => {
vec![CheckCode::PLC0414, CheckCode::PLC2201, CheckCode::PLC3002]
}
Expand Down Expand Up @@ -2261,6 +2263,7 @@ impl CheckCodePrefix {
CheckCodePrefix::PGH00 => SuffixLength::Two,
CheckCodePrefix::PGH001 => SuffixLength::Three,
CheckCodePrefix::PGH002 => SuffixLength::Three,
CheckCodePrefix::PGH003 => SuffixLength::Three,
CheckCodePrefix::PLC => SuffixLength::Zero,
CheckCodePrefix::PLC0 => SuffixLength::One,
CheckCodePrefix::PLC04 => SuffixLength::Two,
Expand Down
1 change: 1 addition & 0 deletions src/pygrep_hooks/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ mod tests {
#[test_case(CheckCode::PGH001, Path::new("PGH001_1.py"); "PGH001_1")]
#[test_case(CheckCode::PGH002, Path::new("PGH002_0.py"); "PGH002_0")]
#[test_case(CheckCode::PGH002, Path::new("PGH002_1.py"); "PGH002_1")]
#[test_case(CheckCode::PGH003, Path::new("PGH003_0.py"); "PGH003_0")]
fn checks(check_code: CheckCode, path: &Path) -> Result<()> {
let snapshot = format!("{}_{}", check_code.as_ref(), path.to_string_lossy());
let mut checks = test_path(
Expand Down
20 changes: 19 additions & 1 deletion src/pygrep_hooks/plugins.rs
Original file line number Diff line number Diff line change
@@ -1,10 +1,15 @@
use rustpython_ast::Expr;
use once_cell::sync::Lazy;
use regex::Regex;
use rustpython_ast::{Expr, Location};

use crate::ast::helpers::{collect_call_paths, dealias_call_path, match_call_path};
use crate::ast::types::Range;
use crate::checkers::ast::Checker;
use crate::checks::{Check, CheckKind};

static BLANKET_TYPE_IGNORE_REGEX: Lazy<Regex> =
Lazy::new(|| Regex::new(r"# type:? *ignore($|\s)").unwrap());

/// PGH002 - deprecated use of logging.warn
pub fn deprecated_log_warn(checker: &mut Checker, func: &Expr) {
let call_path = dealias_call_path(collect_call_paths(func), &checker.import_aliases);
Expand All @@ -17,3 +22,16 @@ pub fn deprecated_log_warn(checker: &mut Checker, func: &Expr) {
));
}
}

/// PGH003 - use of blanket type ignore comments
pub fn blanket_type_ignore(lineno: usize, line: &str) -> Option<Check> {
BLANKET_TYPE_IGNORE_REGEX.find(line).map(|m| {
Check::new(
CheckKind::BlanketTypeIgnore,
Range {
location: Location::new(lineno + 1, m.start()),
end_location: Location::new(lineno + 1, m.end()),
},
)
})
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
---
source: src/pygrep_hooks/mod.rs
expression: checks
---
- kind: BlanketTypeIgnore
location:
row: 1
column: 7
end_location:
row: 1
column: 21
fix: ~
- kind: BlanketTypeIgnore
location:
row: 2
column: 7
end_location:
row: 2
column: 20
fix: ~
- kind: BlanketTypeIgnore
location:
row: 3
column: 7
end_location:
row: 3
column: 20
fix: ~

0 comments on commit f213aff

Please sign in to comment.