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

[flake8-pyi] Implement PYI002, PYI003, PYI004, PYI005 #5457

Merged
merged 5 commits into from
Jul 3, 2023
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
17 changes: 17 additions & 0 deletions crates/ruff/resources/test/fixtures/flake8_pyi/PYI002.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import sys
from sys import platform, version_info

if sys.version == 'Python 2.7.10': ... # PYI002
if 'linux' == sys.platform: ... # PYI002
if hasattr(sys, 'maxint'): ... # PYI002
if sys.maxsize == 42: ... # PYI002
if (2, 7) < sys.version_info < (3, 5): ... # PYI002
if sys.version[0] == 'P': ... # PYI002
if False: ... # PYI002

if version_info[0] == 2: ...
if sys.version_info < (3, 5): ...
if version_info >= (3, 5): ...
if sys.version_info[:2] == (2, 7): ...
if sys.version_info[:1] == (2,): ...
if platform == 'linux': ...
17 changes: 17 additions & 0 deletions crates/ruff/resources/test/fixtures/flake8_pyi/PYI002.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import sys
from sys import platform, version_info

if sys.version == 'Python 2.7.10': ... # PYI002
if 'linux' == sys.platform: ... # PYI002
if hasattr(sys, 'maxint'): ... # PYI002
if sys.maxsize == 42: ... # PYI002
if (2, 7) < sys.version_info < (3, 5): ... # PYI002
if sys.version[0] == 'P': ... # PYI002
if False: ... # PYI002

if version_info[0] == 2: ...
if sys.version_info < (3, 5): ...
if version_info >= (3, 5): ...
if sys.version_info[:2] == (2, 7): ...
if sys.version_info[:1] == (2,): ...
if platform == 'linux': ...
31 changes: 31 additions & 0 deletions crates/ruff/resources/test/fixtures/flake8_pyi/PYI003.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import sys

if sys.version_info[0] == 2: ...
if sys.version_info[0] == True: ... # Y003 Unrecognized sys.version_info check # E712 comparison to True should be 'if cond is True:' or 'if cond:'
if sys.version_info[0.0] == 2: ... # Y003 Unrecognized sys.version_info check
if sys.version_info[False] == 2: ... # Y003 Unrecognized sys.version_info check
if sys.version_info[0j] == 2: ... # Y003 Unrecognized sys.version_info check
if sys.version_info[0] == (2, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[0] == '2': ... # Y003 Unrecognized sys.version_info check
if sys.version_info[1:] >= (7, 11): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[::-1] < (11, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:3] >= (2, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:True] >= (2, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:1] == (2,): ...
if sys.version_info[:1] == (True,): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:1] == (2, 7): ... # Y005 Version comparison must be against a length-1 tuple
if sys.version_info[:2] == (2, 7): ...
if sys.version_info[:2] == (2,): ... # Y005 Version comparison must be against a length-2 tuple
if sys.version_info[:2] == "lol": ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:2.0] >= (3, 9): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:2j] >= (3, 9): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:, :] >= (2, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info < [3, 0]: ... # Y003 Unrecognized sys.version_info check
if sys.version_info < ('3', '0'): ... # Y003 Unrecognized sys.version_info check
if sys.version_info >= (3, 4, 3): ... # Y004 Version comparison must use only major and minor version
if sys.version_info == (3, 4): ... # Y006 Use only < and >= for version comparisons
if sys.version_info > (3, 0): ... # Y006 Use only < and >= for version comparisons
if sys.version_info <= (3, 0): ... # Y006 Use only < and >= for version comparisons
if sys.version_info < (3, 5): ...
if sys.version_info >= (3, 5): ...
if (2, 7) <= sys.version_info < (3, 5): ... # Y002 If test must be a simple comparison against sys.platform or sys.version_info
31 changes: 31 additions & 0 deletions crates/ruff/resources/test/fixtures/flake8_pyi/PYI003.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import sys

if sys.version_info[0] == 2: ...
if sys.version_info[0] == True: ... # Y003 Unrecognized sys.version_info check # E712 comparison to True should be 'if cond is True:' or 'if cond:'
if sys.version_info[0.0] == 2: ... # Y003 Unrecognized sys.version_info check
if sys.version_info[False] == 2: ... # Y003 Unrecognized sys.version_info check
if sys.version_info[0j] == 2: ... # Y003 Unrecognized sys.version_info check
if sys.version_info[0] == (2, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[0] == '2': ... # Y003 Unrecognized sys.version_info check
if sys.version_info[1:] >= (7, 11): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[::-1] < (11, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:3] >= (2, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:True] >= (2, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:1] == (2,): ...
if sys.version_info[:1] == (True,): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:1] == (2, 7): ... # Y005 Version comparison must be against a length-1 tuple
if sys.version_info[:2] == (2, 7): ...
if sys.version_info[:2] == (2,): ... # Y005 Version comparison must be against a length-2 tuple
if sys.version_info[:2] == "lol": ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:2.0] >= (3, 9): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:2j] >= (3, 9): ... # Y003 Unrecognized sys.version_info check
if sys.version_info[:, :] >= (2, 7): ... # Y003 Unrecognized sys.version_info check
if sys.version_info < [3, 0]: ... # Y003 Unrecognized sys.version_info check
if sys.version_info < ('3', '0'): ... # Y003 Unrecognized sys.version_info check
if sys.version_info >= (3, 4, 3): ... # Y004 Version comparison must use only major and minor version
if sys.version_info == (3, 4): ... # Y006 Use only < and >= for version comparisons
if sys.version_info > (3, 0): ... # Y006 Use only < and >= for version comparisons
if sys.version_info <= (3, 0): ... # Y006 Use only < and >= for version comparisons
if sys.version_info < (3, 5): ...
if sys.version_info >= (3, 5): ...
if (2, 7) <= sys.version_info < (3, 5): ... # Y002 If test must be a simple comparison against sys.platform or sys.version_info
15 changes: 15 additions & 0 deletions crates/ruff/resources/test/fixtures/flake8_pyi/PYI004.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import sys
from sys import version_info

if sys.version_info >= (3, 4, 3): ... # PYI004
if sys.version_info < (3, 4, 3): ... # PYI004
if sys.version_info == (3, 4, 3): ... # PYI004
if sys.version_info != (3, 4, 3): ... # PYI004

if sys.version_info[0] == 2: ...
if version_info[0] == 2: ...
if sys.version_info < (3, 5): ...
if version_info >= (3, 5): ...
if sys.version_info[:2] == (2, 7): ...
if sys.version_info[:1] == (2,): ...
if sys.platform == 'linux': ...
15 changes: 15 additions & 0 deletions crates/ruff/resources/test/fixtures/flake8_pyi/PYI004.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import sys
from sys import version_info

if sys.version_info >= (3, 4, 3): ... # PYI004
if sys.version_info < (3, 4, 3): ... # PYI004
if sys.version_info == (3, 4, 3): ... # PYI004
if sys.version_info != (3, 4, 3): ... # PYI004

if sys.version_info[0] == 2: ...
if version_info[0] == 2: ...
if sys.version_info < (3, 5): ...
if version_info >= (3, 5): ...
if sys.version_info[:2] == (2, 7): ...
if sys.version_info[:1] == (2,): ...
if sys.platform == 'linux': ...
14 changes: 14 additions & 0 deletions crates/ruff/resources/test/fixtures/flake8_pyi/PYI005.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import sys
from sys import platform, version_info

if sys.version_info[:1] == (2, 7): ... # Y005
if sys.version_info[:2] == (2,): ... # Y005


if sys.version_info[0] == 2: ...
if version_info[0] == 2: ...
if sys.version_info < (3, 5): ...
if version_info >= (3, 5): ...
if sys.version_info[:2] == (2, 7): ...
if sys.version_info[:1] == (2,): ...
if platform == 'linux': ...
14 changes: 14 additions & 0 deletions crates/ruff/resources/test/fixtures/flake8_pyi/PYI005.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import sys
from sys import platform, version_info

if sys.version_info[:1] == (2, 7): ... # Y005
if sys.version_info[:2] == (2,): ... # Y005


if sys.version_info[0] == 2: ...
if version_info[0] == 2: ...
if sys.version_info < (3, 5): ...
if version_info >= (3, 5): ...
if sys.version_info[:2] == (2, 7): ...
if sys.version_info[:1] == (2,): ...
if platform == 'linux': ...
10 changes: 10 additions & 0 deletions crates/ruff/src/checkers/ast/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1371,6 +1371,16 @@ where
self.diagnostics.push(diagnostic);
}
}
if self.is_stub {
if self.any_enabled(&[
Rule::ComplexIfStatementInStub,
Rule::UnrecognizedVersionInfoCheck,
Rule::PatchVersionComparison,
Rule::WrongTupleLengthVersionComparison,
]) {
flake8_pyi::rules::version_info(self, test);
}
}
}
Stmt::Assert(ast::StmtAssert {
test,
Expand Down
4 changes: 4 additions & 0 deletions crates/ruff/src/codes.rs
Original file line number Diff line number Diff line change
Expand Up @@ -596,6 +596,10 @@ pub fn code_to_rule(linter: Linter, code: &str) -> Option<(RuleGroup, Rule)> {

// flake8-pyi
(Flake8Pyi, "001") => (RuleGroup::Unspecified, rules::flake8_pyi::rules::UnprefixedTypeParam),
(Flake8Pyi, "002") => (RuleGroup::Unspecified, rules::flake8_pyi::rules::ComplexIfStatementInStub),
(Flake8Pyi, "003") => (RuleGroup::Unspecified, rules::flake8_pyi::rules::UnrecognizedVersionInfoCheck),
(Flake8Pyi, "004") => (RuleGroup::Unspecified, rules::flake8_pyi::rules::PatchVersionComparison),
(Flake8Pyi, "005") => (RuleGroup::Unspecified, rules::flake8_pyi::rules::WrongTupleLengthVersionComparison),
(Flake8Pyi, "006") => (RuleGroup::Unspecified, rules::flake8_pyi::rules::BadVersionInfoComparison),
(Flake8Pyi, "007") => (RuleGroup::Unspecified, rules::flake8_pyi::rules::UnrecognizedPlatformCheck),
(Flake8Pyi, "008") => (RuleGroup::Unspecified, rules::flake8_pyi::rules::UnrecognizedPlatformName),
Expand Down
2 changes: 1 addition & 1 deletion crates/ruff/src/registry/rule_set.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ use ruff_macros::CacheKey;
use std::fmt::{Debug, Formatter};
use std::iter::FusedIterator;

const RULESET_SIZE: usize = 10;
const RULESET_SIZE: usize = 11;

/// A set of [`Rule`]s.
///
Expand Down
8 changes: 8 additions & 0 deletions crates/ruff/src/rules/flake8_pyi/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,8 @@ mod tests {
#[test_case(Rule::BadVersionInfoComparison, Path::new("PYI006.pyi"))]
#[test_case(Rule::CollectionsNamedTuple, Path::new("PYI024.py"))]
#[test_case(Rule::CollectionsNamedTuple, Path::new("PYI024.pyi"))]
#[test_case(Rule::ComplexIfStatementInStub, Path::new("PYI002.py"))]
#[test_case(Rule::ComplexIfStatementInStub, Path::new("PYI002.pyi"))]
#[test_case(Rule::DocstringInStub, Path::new("PYI021.py"))]
#[test_case(Rule::DocstringInStub, Path::new("PYI021.pyi"))]
#[test_case(Rule::DuplicateUnionMember, Path::new("PYI016.py"))]
Expand Down Expand Up @@ -56,6 +58,8 @@ mod tests {
#[test_case(Rule::TSuffixedTypeAlias, Path::new("PYI043.pyi"))]
#[test_case(Rule::FutureAnnotationsInStub, Path::new("PYI044.py"))]
#[test_case(Rule::FutureAnnotationsInStub, Path::new("PYI044.pyi"))]
#[test_case(Rule::PatchVersionComparison, Path::new("PYI004.py"))]
#[test_case(Rule::PatchVersionComparison, Path::new("PYI004.pyi"))]
#[test_case(Rule::TypeCommentInStub, Path::new("PYI033.py"))]
#[test_case(Rule::TypeCommentInStub, Path::new("PYI033.pyi"))]
#[test_case(Rule::TypedArgumentDefaultInStub, Path::new("PYI011.py"))]
Expand All @@ -72,6 +76,10 @@ mod tests {
#[test_case(Rule::UnrecognizedPlatformCheck, Path::new("PYI007.pyi"))]
#[test_case(Rule::UnrecognizedPlatformName, Path::new("PYI008.py"))]
#[test_case(Rule::UnrecognizedPlatformName, Path::new("PYI008.pyi"))]
#[test_case(Rule::UnrecognizedVersionInfoCheck, Path::new("PYI003.py"))]
#[test_case(Rule::UnrecognizedVersionInfoCheck, Path::new("PYI003.pyi"))]
#[test_case(Rule::WrongTupleLengthVersionComparison, Path::new("PYI005.py"))]
#[test_case(Rule::WrongTupleLengthVersionComparison, Path::new("PYI005.pyi"))]
fn rules(rule_code: Rule, path: &Path) -> Result<()> {
let snapshot = format!("{}_{}", rule_code.noqa_code(), path.to_string_lossy());
let diagnostics = test_path(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ pub struct BadVersionInfoComparison;
impl Violation for BadVersionInfoComparison {
#[derive_message_formats]
fn message(&self) -> String {
format!("Use `<` or `>=` for version info comparisons")
format!("Use `<` or `>=` for `sys.version_info` comparisons")
}
}

Expand All @@ -78,8 +78,10 @@ pub(crate) fn bad_version_info_comparison(
return;
}

if !matches!(op, CmpOp::Lt | CmpOp::GtE) {
let diagnostic = Diagnostic::new(BadVersionInfoComparison, expr.range());
checker.diagnostics.push(diagnostic);
if matches!(op, CmpOp::Lt | CmpOp::GtE) {
return;
}

let diagnostic = Diagnostic::new(BadVersionInfoComparison, expr.range());
checker.diagnostics.push(diagnostic);
}
2 changes: 2 additions & 0 deletions crates/ruff/src/rules/flake8_pyi/rules/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ pub(crate) use type_alias_naming::*;
pub(crate) use type_comment_in_stub::*;
pub(crate) use unaliased_collections_abc_set_import::*;
pub(crate) use unrecognized_platform::*;
pub(crate) use version_info::*;

mod any_eq_ne_annotation;
mod bad_version_info_comparison;
Expand All @@ -47,3 +48,4 @@ mod type_alias_naming;
mod type_comment_in_stub;
mod unaliased_collections_abc_set_import;
mod unrecognized_platform;
mod version_info;
Loading