mirror of https://github.com/astral-sh/ruff
Recursively resolve `TypeDicts` for N815 violations (#10719)
## Summary Only works within a single file for now. Closes https://github.com/astral-sh/ruff/issues/10671.
This commit is contained in:
parent
200ebeebdc
commit
67f0f615b2
|
|
@ -21,3 +21,10 @@ class D(TypedDict):
|
|||
mixedCase: bool
|
||||
_mixedCase: list
|
||||
mixed_Case: set
|
||||
|
||||
class E(D):
|
||||
lower: int
|
||||
CONSTANT: str
|
||||
mixedCase: bool
|
||||
_mixedCase: list
|
||||
mixed_Case: set
|
||||
|
|
|
|||
|
|
@ -223,14 +223,10 @@ pub(crate) fn expression(expr: &Expr, checker: &mut Checker) {
|
|||
}
|
||||
}
|
||||
if checker.enabled(Rule::MixedCaseVariableInClassScope) {
|
||||
if let ScopeKind::Class(ast::StmtClassDef { arguments, .. }) =
|
||||
&checker.semantic.current_scope().kind
|
||||
if let ScopeKind::Class(class_def) = &checker.semantic.current_scope().kind
|
||||
{
|
||||
pep8_naming::rules::mixed_case_variable_in_class_scope(
|
||||
checker,
|
||||
expr,
|
||||
id,
|
||||
arguments.as_deref(),
|
||||
checker, expr, id, class_def,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,8 +1,8 @@
|
|||
use itertools::Itertools;
|
||||
|
||||
use ruff_python_ast::name::UnqualifiedName;
|
||||
use ruff_python_ast::{self as ast, Arguments, Expr, Stmt};
|
||||
use ruff_python_semantic::SemanticModel;
|
||||
use ruff_python_ast::{self as ast, Expr, Stmt};
|
||||
use ruff_python_semantic::{analyze, SemanticModel};
|
||||
use ruff_python_stdlib::str::{is_cased_lowercase, is_cased_uppercase};
|
||||
|
||||
pub(super) fn is_camelcase(name: &str) -> bool {
|
||||
|
|
@ -86,16 +86,13 @@ pub(super) fn is_type_alias_assignment(stmt: &Stmt, semantic: &SemanticModel) ->
|
|||
}
|
||||
|
||||
/// Returns `true` if the statement is an assignment to a `TypedDict`.
|
||||
pub(super) fn is_typed_dict_class(arguments: Option<&Arguments>, semantic: &SemanticModel) -> bool {
|
||||
pub(super) fn is_typed_dict_class(class_def: &ast::StmtClassDef, semantic: &SemanticModel) -> bool {
|
||||
if !semantic.seen_typing() {
|
||||
return false;
|
||||
}
|
||||
|
||||
arguments.is_some_and(|arguments| {
|
||||
arguments
|
||||
.args
|
||||
.iter()
|
||||
.any(|base| semantic.match_typing_expr(base, "TypedDict"))
|
||||
analyze::class::any_qualified_name(class_def, semantic, &|qualified_name| {
|
||||
semantic.match_typing_qualified_name(&qualified_name, "TypedDict")
|
||||
})
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,7 +1,6 @@
|
|||
use ruff_python_ast::{Arguments, Expr};
|
||||
|
||||
use ruff_diagnostics::{Diagnostic, Violation};
|
||||
use ruff_macros::{derive_message_formats, violation};
|
||||
use ruff_python_ast::{self as ast, Expr};
|
||||
use ruff_text_size::Ranged;
|
||||
|
||||
use crate::checkers::ast::Checker;
|
||||
|
|
@ -55,7 +54,7 @@ pub(crate) fn mixed_case_variable_in_class_scope(
|
|||
checker: &mut Checker,
|
||||
expr: &Expr,
|
||||
name: &str,
|
||||
arguments: Option<&Arguments>,
|
||||
class_def: &ast::StmtClassDef,
|
||||
) {
|
||||
if !helpers::is_mixed_case(name) {
|
||||
return;
|
||||
|
|
@ -64,7 +63,7 @@ pub(crate) fn mixed_case_variable_in_class_scope(
|
|||
let parent = checker.semantic().current_statement();
|
||||
|
||||
if helpers::is_named_tuple_assignment(parent, checker.semantic())
|
||||
|| helpers::is_typed_dict_class(arguments, checker.semantic())
|
||||
|| helpers::is_typed_dict_class(class_def, checker.semantic())
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue