def visit_func_def(self, node: FuncDef) -> FuncDef: # Note that a FuncDef must be transformed to a FuncDef. new = FuncDef(node.name(), [self.visit_var(var) for var in node.args], node.arg_kinds[:], [None] * len(node.init), self.block(node.body), self.optional_type(node.type)) self.copy_function_attributes(new, node) new._fullname = node._fullname new.is_decorated = node.is_decorated new.is_conditional = node.is_conditional new.is_abstract = node.is_abstract new.is_static = node.is_static new.is_property = node.is_property new.original_def = node.original_def return new
def visit_func_def(self, node: FuncDef) -> FuncDef: # Note that a FuncDef must be transformed to a FuncDef. new = FuncDef(node.name(), [self.copy_argument(arg) for arg in node.arguments], self.block(node.body), cast(FunctionLike, self.optional_type(node.type))) self.copy_function_attributes(new, node) new._fullname = node._fullname new.is_decorated = node.is_decorated new.is_conditional = node.is_conditional new.is_abstract = node.is_abstract new.is_static = node.is_static new.is_class = node.is_class new.is_property = node.is_property new.original_def = node.original_def return new
def visit_func_def(self, node: FuncDef) -> FuncDef: # Note that a FuncDef must be transformed to a FuncDef. # These contortions are needed to handle the case of recursive # references inside the function being transformed. # Set up placeholder nodes for references within this function # to other functions defined inside it. # Don't create an entry for this function itself though, # since we want self-references to point to the original # function if this is the top-level node we are transforming. init = FuncMapInitializer(self) for stmt in node.body.body: stmt.accept(init) new = FuncDef(node.name, [self.copy_argument(arg) for arg in node.arguments], self.block(node.body), cast(Optional[FunctionLike], self.optional_type(node.type))) self.copy_function_attributes(new, node) new._fullname = node._fullname new.is_decorated = node.is_decorated new.is_conditional = node.is_conditional new.is_abstract = node.is_abstract new.is_static = node.is_static new.is_class = node.is_class new.is_property = node.is_property new.is_final = node.is_final new.original_def = node.original_def if node in self.func_placeholder_map: # There is a placeholder definition for this function. Replace # the attributes of the placeholder with those form the transformed # function. We know that the classes will be identical (otherwise # this wouldn't work). result = self.func_placeholder_map[node] replace_object_state(result, new) return result else: return new
def visit_func_def(self, node: FuncDef) -> FuncDef: # Note that a FuncDef must be transformed to a FuncDef. # These contortions are needed to handle the case of recursive # references inside the function being transformed. # Set up placeholder nodes for references within this function # to other functions defined inside it. # Don't create an entry for this function itself though, # since we want self-references to point to the original # function if this is the top-level node we are transforming. init = FuncMapInitializer(self) for stmt in node.body.body: stmt.accept(init) new = FuncDef(node.name(), [self.copy_argument(arg) for arg in node.arguments], self.block(node.body), cast(Optional[FunctionLike], self.optional_type(node.type))) self.copy_function_attributes(new, node) new._fullname = node._fullname new.is_decorated = node.is_decorated new.is_conditional = node.is_conditional new.is_abstract = node.is_abstract new.is_static = node.is_static new.is_class = node.is_class new.is_property = node.is_property new.is_final = node.is_final new.original_def = node.original_def if node in self.func_placeholder_map: # There is a placeholder definition for this function. Replace # the attributes of the placeholder with those form the transformed # function. We know that the classes will be identical (otherwise # this wouldn't work). result = self.func_placeholder_map[node] replace_object_state(result, new) return result else: return new
def _adjust_interface_function( self, api: SemanticAnalyzerPluginInterface, class_info: TypeInfo, func_def: FuncDef, ) -> Statement: if func_def.arg_names and func_def.arg_names[0] == "self": # reveal the common mistake of leaving "self" arguments in the # interface api.fail("Interface methods should not have 'self' argument", func_def) else: selftype = Instance(class_info, [], line=class_info.line, column=class_info.column) selfarg = Argument(Var("self", None), selftype, None, ARG_POS) if isinstance(func_def.type, CallableType): func_def.type.arg_names.insert(0, "self") func_def.type.arg_kinds.insert(0, ARG_POS) func_def.type.arg_types.insert(0, selftype) func_def.arg_names.insert(0, "self") func_def.arg_kinds.insert(0, ARG_POS) func_def.arguments.insert(0, selfarg) func_def.is_abstract = True if func_def.name() in ("__getattr__", "__getattribute__"): # These special methods cannot be decorated. Likely a mypy bug. return func_def func_def.is_decorated = True var = Var(func_def.name(), func_def.type) var.is_initialized_in_class = True var.info = func_def.info var.set_line(func_def.line) decor = Decorator(func_def, [], var) return decor