@@ -54,8 +54,11 @@ def err(self, node, code: str, **kwargs):
5454 return lineno , col_offset + 1 , f'{ code } { code_str } ' , self
5555
5656
57- def _ignored (name , ignore ):
58- return any (fnmatchcase (name , i ) for i in ignore )
57+ class NameSet (frozenset [str ]):
58+ """A set of names that are matched using fnmatchcase."""
59+
60+ def __contains__ (self , item ) -> bool :
61+ return any (fnmatchcase (item , name ) for name in self )
5962
6063
6164class _FunctionType :
@@ -65,7 +68,7 @@ class _FunctionType:
6568 METHOD = 'method'
6669
6770
68- _default_ignore_names = [
71+ _default_ignored_names = [
6972 'setUp' ,
7073 'tearDown' ,
7174 'setUpClass' ,
@@ -98,7 +101,7 @@ class NamingChecker:
98101 visitors = BaseASTCheck .all
99102 decorator_to_type = _build_decorator_to_type (
100103 _default_classmethod_decorators , _default_staticmethod_decorators )
101- ignore_names = frozenset ( _default_ignore_names )
104+ ignored = NameSet ( _default_ignored_names )
102105
103106 def __init__ (self , tree , filename ):
104107 self .tree = tree
@@ -107,7 +110,7 @@ def __init__(self, tree, filename):
107110 def add_options (cls , parser ):
108111 parser .add_option (
109112 '--ignore-names' ,
110- default = _default_ignore_names ,
113+ default = _default_ignored_names ,
111114 parse_from_config = True ,
112115 comma_separated_list = True ,
113116 help = 'List of names or glob patterns the pep8-naming '
@@ -135,14 +138,14 @@ def add_options(cls, parser):
135138
136139 @classmethod
137140 def parse_options (cls , options ):
138- cls .ignore_names = frozenset (options .ignore_names )
141+ cls .ignored = NameSet (options .ignore_names )
139142 cls .decorator_to_type = _build_decorator_to_type (
140143 options .classmethod_decorators ,
141144 options .staticmethod_decorators )
142145
143- # Build a list of node visitors based the error codes that have been
144- # selected in the style guide. Only the checks that have been selected
145- # will be evaluated as a performance optimization.
146+ # Rebuild the list of node visitors based the error codes that have
147+ # been selected in the style guide. Only the checks that have been
148+ # selected will be evaluated as a performance optimization.
146149 engine = style_guide .DecisionEngine (options )
147150 cls .visitors = frozenset (
148151 visitor for visitor in BaseASTCheck .all for code in visitor .codes
@@ -166,12 +169,12 @@ def visit_node(self, node, parents: Iterable):
166169 self .find_global_defs (node )
167170
168171 method = 'visit_' + node .__class__ .__name__ .lower ()
169- ignore_names = self .ignore_names
172+ ignored = self .ignored
170173 for visitor in self .visitors :
171174 visitor_method = getattr (visitor , method , None )
172175 if visitor_method is None :
173176 continue
174- yield from visitor_method (node , parents , ignore_names )
177+ yield from visitor_method (node , parents , ignored )
175178
176179 def tag_class_functions (self , cls_node ):
177180 """Tag functions if they are methods, classmethods, staticmethods"""
@@ -273,9 +276,9 @@ def superclass_names(cls, name, parents: Iterable, _names=None):
273276 names .update (cls .superclass_names (base .id , parents , names ))
274277 return names
275278
276- def visit_classdef (self , node , parents : Iterable , ignore = None ):
279+ def visit_classdef (self , node , parents : Iterable , ignored : NameSet ):
277280 name = node .name
278- if _ignored ( name , ignore ) :
281+ if name in ignored :
279282 return
280283 name = name .strip ('_' )
281284 if not name [:1 ].isupper () or '_' in name :
@@ -308,10 +311,10 @@ def has_override_decorator(node):
308311 return True
309312 return False
310313
311- def visit_functiondef (self , node , parents : Iterable , ignore = None ):
314+ def visit_functiondef (self , node , parents : Iterable , ignored : NameSet ):
312315 function_type = getattr (node , 'function_type' , _FunctionType .FUNCTION )
313316 name = node .name
314- if _ignored ( name , ignore ) :
317+ if name in ignored :
315318 return
316319 if name in ('__dir__' , '__getattr__' ):
317320 return
@@ -339,18 +342,18 @@ class FunctionArgNamesCheck(BaseASTCheck):
339342 N804 = "first argument of a classmethod should be named 'cls'"
340343 N805 = "first argument of a method should be named 'self'"
341344
342- def visit_functiondef (self , node , parents : Iterable , ignore = None ):
345+ def visit_functiondef (self , node , parents : Iterable , ignored : NameSet ):
343346 args = node .args .posonlyargs + node .args .args + node .args .kwonlyargs
344347
345348 # Start by applying checks that are specific to the first argument.
346349 #
347- # Note: The `ignore ` check shouldn't be necessary here because we'd
350+ # Note: The `ignored ` check shouldn't be necessary here because we'd
348351 # expect users to explicitly ignore N804/N805 when using names
349352 # other than `self` and `cls` rather than ignoring names like
350353 # `klass` to get around these checks. However, a previous
351354 # implementation allowed for that, so we retain that behavior
352355 # for backwards compatibility.
353- if args and (name := args [0 ].arg ) and not _ignored ( name , ignore ) :
356+ if args and (name := args [0 ].arg ) and name not in ignored :
354357 function_type = getattr (node , 'function_type' , None )
355358 if function_type == _FunctionType .METHOD and name != 'self' :
356359 yield self .err (args [0 ], 'N805' )
@@ -368,7 +371,7 @@ def visit_functiondef(self, node, parents: Iterable, ignore=None):
368371
369372 for arg in args :
370373 name = arg .arg
371- if name .lower () != name and not _ignored ( name , ignore ) :
374+ if name .lower () != name and name not in ignored :
372375 yield self .err (arg , 'N803' , name = name )
373376
374377 visit_asyncfunctiondef = visit_functiondef
@@ -384,7 +387,7 @@ class ImportAsCheck(BaseASTCheck):
384387 N814 = "camelcase '{name}' imported as constant '{asname}'"
385388 N817 = "camelcase '{name}' imported as acronym '{asname}'"
386389
387- def visit_importfrom (self , node , parents : Iterable , ignore = None ):
390+ def visit_importfrom (self , node , parents : Iterable , ignored : NameSet ):
388391 for name in node .names :
389392 asname = name .asname
390393 if not asname :
@@ -416,7 +419,7 @@ class VariablesCheck(BaseASTCheck):
416419 N815 = "variable '{name}' in class scope should not be mixedCase"
417420 N816 = "variable '{name}' in global scope should not be mixedCase"
418421
419- def _find_errors (self , assignment_target , parents : Iterable , ignore ):
422+ def _find_errors (self , assignment_target , parents : Iterable , ignored : NameSet ):
420423 for parent_func in reversed (parents ):
421424 if isinstance (parent_func , ast .ClassDef ):
422425 checker = self .class_variable_check
@@ -427,7 +430,7 @@ def _find_errors(self, assignment_target, parents: Iterable, ignore):
427430 else :
428431 checker = self .global_variable_check
429432 for name in _extract_names (assignment_target ):
430- if _ignored ( name , ignore ) :
433+ if name in ignored :
431434 continue
432435 error_code = checker (name )
433436 if error_code :
@@ -444,38 +447,38 @@ def is_namedtupe(node_value):
444447 return True
445448 return False
446449
447- def visit_assign (self , node , parents : Iterable , ignore = None ):
450+ def visit_assign (self , node , parents : Iterable , ignored : NameSet ):
448451 if self .is_namedtupe (node .value ):
449452 return
450453 for target in node .targets :
451- yield from self ._find_errors (target , parents , ignore )
454+ yield from self ._find_errors (target , parents , ignored )
452455
453- def visit_namedexpr (self , node , parents : Iterable , ignore ):
456+ def visit_namedexpr (self , node , parents : Iterable , ignored : NameSet ):
454457 if self .is_namedtupe (node .value ):
455458 return
456- yield from self ._find_errors (node .target , parents , ignore )
459+ yield from self ._find_errors (node .target , parents , ignored )
457460
458461 visit_annassign = visit_namedexpr
459462
460- def visit_with (self , node , parents : Iterable , ignore ):
463+ def visit_with (self , node , parents : Iterable , ignored : NameSet ):
461464 for item in node .items :
462465 yield from self ._find_errors (
463- item .optional_vars , parents , ignore )
466+ item .optional_vars , parents , ignored )
464467
465468 visit_asyncwith = visit_with
466469
467- def visit_for (self , node , parents : Iterable , ignore ):
468- yield from self ._find_errors (node .target , parents , ignore )
470+ def visit_for (self , node , parents : Iterable , ignored : NameSet ):
471+ yield from self ._find_errors (node .target , parents , ignored )
469472
470473 visit_asyncfor = visit_for
471474
472- def visit_excepthandler (self , node , parents : Iterable , ignore ):
475+ def visit_excepthandler (self , node , parents : Iterable , ignored : NameSet ):
473476 if node .name :
474- yield from self ._find_errors (node , parents , ignore )
477+ yield from self ._find_errors (node , parents , ignored )
475478
476- def visit_generatorexp (self , node , parents : Iterable , ignore ):
479+ def visit_generatorexp (self , node , parents : Iterable , ignored : NameSet ):
477480 for gen in node .generators :
478- yield from self ._find_errors (gen .target , parents , ignore )
481+ yield from self ._find_errors (gen .target , parents , ignored )
479482
480483 visit_listcomp = visit_dictcomp = visit_setcomp = visit_generatorexp
481484
@@ -502,7 +505,7 @@ class TypeVarNameCheck(BaseASTCheck):
502505 N808 = "type variable name '{name}' should use CapWords convention " \
503506 "and an optional '_co' or '_contra' suffix"
504507
505- def visit_module (self , node , parents : Iterable , ignore = None ):
508+ def visit_module (self , node , parents : Iterable , ignored : NameSet ):
506509 for body in node .body :
507510 try :
508511 if len (body .targets ) != 1 :
@@ -514,7 +517,7 @@ def visit_module(self, node, parents: Iterable, ignore=None):
514517 except AttributeError :
515518 continue
516519
517- if func_name != "TypeVar" or _ignored ( name , ignore ) :
520+ if func_name != "TypeVar" or name in ignored :
518521 continue
519522
520523 if len (args ) == 0 or args [0 ] != name :
0 commit comments