def visit_module(self, node: nodes.Module) -> None: """Visit an astroid.Module node. * set the locals_type mapping * set the depends mapping * optionally tag the node with a unique id """ if hasattr(node, "locals_type"): return node.locals_type = collections.defaultdict(list) node.depends = [] if self.tag: node.uid = self.generate_id()
def process_module(self, node: nodes.Module) -> None: """inspect the source file to find encoding problem""" encoding = node.file_encoding if node.file_encoding else "ascii" with node.stream() as stream: for lineno, line in enumerate(stream): self._check_encoding(lineno + 1, line, encoding)
def process_module(self, node: nodes.Module) -> None: with node.stream() as stream: for (line_num, line) in enumerate(stream): line = line.rstrip() if line.endswith(b"#"): if not is_line_commented(line[:-1]): self.add_message("empty-comment", line=line_num + 1)
def process_module(self, node: nodes.Module) -> None: """process a module the module's content is accessible via the stream object stream must implement the readlines method """ with node.stream() as stream: self.append_stream(self.linter.current_name, stream, node.file_encoding)
def process_module(self, node: nodes.Module) -> None: """Process a module. the module's content is accessible via node.stream() function """ with node.stream() as stream: for (lineno, line) in enumerate(stream): if line.rstrip().endswith("\\"): self.add_message("backslash-line-continuation", line=lineno)
def process_module(self, node: nodes.Module) -> None: r"""Check whether the copyright notice is correctly placed in the source file of a module. Compare the first lines of a source file against the standard copyright notice (i.e., the `golden` variable below). Suffix whitespace (including newline symbols) is not considered during the comparison. Pylint will report a message if the copyright notice is not correctly placed. Args: node: the module to be checked. """ # Exit if the checker is disabled in the source file. if not self.linter.is_message_enabled( "wrong-or-nonexistent-copyright-notice"): return golden = [ b'# Copyright 20XX The Cirq Developers', b'#', b'# Licensed under the Apache License, Version 2.0 (the "License");', b'# you may not use this file except in compliance with the License.', b'# You may obtain a copy of the License at', b'#', b'# https://www.apache.org/licenses/LICENSE-2.0', b'#', b'# Unless required by applicable law or agreed to in writing, software', b'# distributed under the License is distributed on an "AS IS" BASIS,', b'# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.', b'# See the License for the specific language governing permissions and', b'# limitations under the License.', ] with node.stream() as stream: for expected_line, (lineno, line) in zip(golden, enumerate(stream)): for expected_char, (colno, char) in zip(expected_line, enumerate(line)): # The text needs to be same as the template except for the year. if expected_char != char and not (lineno == 0 and 14 <= colno <= 15): self.add_message( "wrong-or-nonexistent-copyright-notice", line=lineno + 1, col_offset=colno, ) return # The line cannot be shorter than the template or contain extra text. if len(line) < len(expected_line) or line[ len(expected_line):].strip() != b'': self.add_message( "wrong-or-nonexistent-copyright-notice", line=lineno + 1, col_offset=min(len(line), len(expected_line)), ) return
def visit_module(self, module: nodes.Module) -> None: self.cfgs[module] = ControlFlowGraph() self._current_cfg = self.cfgs[module] self._current_block = self._current_cfg.start module.cfg_block = self._current_cfg.start for child in module.body: child.accept(self) self._current_cfg.link_or_merge(self._current_block, self._current_cfg.end) self._current_cfg.update_block_reachability()
def _get_provides_from_name(mod: Module, name: str, pkgfiles: Set[str]): _, node_list = mod.lookup(name) node = node_list[-1] if isinstance(node, Import): return set() # import are always outside of package elif isinstance(node, ImportFrom): return _process_import_from(node, name, pkgfiles) elif isinstance(node, ClassDef): return _process_class_node(node, pkgfiles) elif isinstance(node, (FunctionDef, AssignName)): return {node.name} raise AssertionError('Unsupported type of public symbol: {}'.format(name))
def get_module(self, name: str, node: nodes.Module) -> PackageEntity: """Return a module by its name, looking also for relative imports; raise KeyError if not found. """ for mod in self.modules(): mod_name = mod.node.name if mod_name == name: return mod # search for fullname of relative import modules package = node.root().name if mod_name == f"{package}.{name}": return mod if mod_name == f"{package.rsplit('.', 1)[0]}.{name}": return mod raise KeyError(name)
def _parse_functions(self, module: nodes.Module) -> None: """Parse the function definitions from typeshed.""" for function_def in module.nodes_of_class(nodes.FunctionDef): in_class = isinstance(function_def.parent, nodes.ClassDef) if in_class: tvars = self.classes[function_def.parent.name]["__pyta_tvars"] else: tvars = [] f_type = parse_annotations(function_def, tvars) if in_class: self.classes[function_def.parent.name][ function_def.name].extend(f_type) self.methods[function_def.name].extend(f_type) else: self.functions[function_def.name].extend(f_type)
def process_module(self, node: nodes.Module) -> None: """Perform the actual check by checking module stream.""" with node.stream() as stream: codec, codec_line = self._determine_codec(stream) self._check_codec(codec, codec_line) stream.seek(0) # Check for invalid content (controls/chars) for (lineno, line) in enumerate(_fix_utf16_32_line_stream(stream, codec), start=1): if lineno == 1: line = _remove_bom(line, codec) self._check_bidi_chars(line, lineno, codec) self._check_invalid_chars(line, lineno, codec)
def process_module(self, node: nodes.Module) -> None: """Process a module. the module's content is accessible via the stream object stream must implement the readlines method """ if self.linter.current_name is None: warnings.warn( ("In pylint 3.0 the current_name attribute of the linter object should be a string. " "If unknown it should be initialized as an empty string."), DeprecationWarning, ) with node.stream() as stream: self.append_stream(self.linter.current_name, stream, node.file_encoding) # type: ignore[arg-type]
def _parse_classes(self, module: nodes.Module) -> None: """Parse the class definitions from typeshed.""" for class_def in module.nodes_of_class(nodes.ClassDef): tvars = [] self.classes[class_def.name]["__bases"] = [] for base in class_def.bases: base_type = _node_to_type(base) self.classes[class_def.name]["__pyta_tvars"] = [ tv.__name__ for tv in _collect_tvars(base_type) ] self.classes[class_def.name]["__bases"].append(base_type) self.classes[class_def.name]["__mro"] = [ cls.name for cls in class_def.mro() ] for node in (nodes[0] for nodes in class_def.locals.values() if isinstance(nodes[0], nodes.AssignName) and isinstance(nodes[0].parent, nodes.AnnAssign)): self.classes[class_def.name][node.name] = parse_annotations( node, tvars)
def _post_build(self, module: nodes.Module, builder: rebuilder.TreeRebuilder, encoding: str) -> nodes.Module: """Handles encoding and delayed nodes after a module has been built""" module.file_encoding = encoding self._manager.cache_module(module) # post tree building steps after we stored the module in the cache: for from_node in builder._import_from_nodes: if from_node.modname == "__future__": for symbol, _ in from_node.names: module.future_imports.add(symbol) self.add_from_names_to_locals(from_node) # handle delayed assattr nodes for delayed in builder._delayed_assattr: self.delayed_assattr(delayed) # Visit the transforms if self._apply_transforms: module = self._manager.visit_transforms(module) return module
def build_module(name, doc=None): """create and initialize a astroid Module node""" node = Module(name, doc, pure_python=False) node.package = False node.parent = None return node
def tokenize_module(node: nodes.Module) -> List[tokenize.TokenInfo]: with node.stream() as stream: readline = stream.readline return list(tokenize.tokenize(readline))