(self, defn: FuncDef)
| 991 | return f"{fullname}#{self.current_overload_item}" |
| 992 | |
| 993 | def analyze_func_def(self, defn: FuncDef) -> None: |
| 994 | if self.push_type_args(defn.type_args, defn) is None: |
| 995 | self.defer(defn) |
| 996 | return |
| 997 | |
| 998 | self.function_stack.append(defn) |
| 999 | |
| 1000 | if defn.type: |
| 1001 | assert isinstance(defn.type, CallableType) |
| 1002 | has_self_type = self.update_function_type_variables(defn.type, defn) |
| 1003 | else: |
| 1004 | has_self_type = False |
| 1005 | |
| 1006 | self.function_stack.pop() |
| 1007 | |
| 1008 | if self.is_class_scope(): |
| 1009 | # Method definition |
| 1010 | assert self.type is not None |
| 1011 | defn.info = self.type |
| 1012 | if defn.type is not None and defn.name in ("__init__", "__init_subclass__"): |
| 1013 | assert isinstance(defn.type, CallableType) |
| 1014 | if isinstance(get_proper_type(defn.type.ret_type), AnyType): |
| 1015 | defn.type = defn.type.copy_modified(ret_type=NoneType()) |
| 1016 | self.prepare_method_signature(defn, self.type, has_self_type) |
| 1017 | |
| 1018 | # Analyze function signature |
| 1019 | fullname = self.function_fullname(defn.fullname) |
| 1020 | with self.tvar_scope_frame(self.tvar_scope.method_frame(fullname)): |
| 1021 | if defn.type: |
| 1022 | self.check_classvar_in_signature(defn.type) |
| 1023 | assert isinstance(defn.type, CallableType) |
| 1024 | # Signature must be analyzed in the surrounding scope so that |
| 1025 | # class-level imported names and type variables are in scope. |
| 1026 | analyzer = self.type_analyzer() |
| 1027 | tag = self.track_incomplete_refs() |
| 1028 | result = analyzer.visit_callable_type(defn.type, nested=False, namespace=fullname) |
| 1029 | # Don't store not ready types (including placeholders). |
| 1030 | if self.found_incomplete_ref(tag) or has_placeholder(result): |
| 1031 | self.defer(defn) |
| 1032 | self.pop_type_args(defn.type_args) |
| 1033 | return |
| 1034 | assert isinstance(result, ProperType) |
| 1035 | if isinstance(result, CallableType): |
| 1036 | # type guards need to have a positional argument, to spec |
| 1037 | skip_self = self.is_class_scope() and not defn.is_static |
| 1038 | if result.type_guard and ARG_POS not in result.arg_kinds[skip_self:]: |
| 1039 | self.fail( |
| 1040 | "TypeGuard functions must have a positional argument", |
| 1041 | result, |
| 1042 | code=codes.VALID_TYPE, |
| 1043 | ) |
| 1044 | # in this case, we just kind of just ... remove the type guard. |
| 1045 | result = result.copy_modified(type_guard=None) |
| 1046 | if result.type_is and ARG_POS not in result.arg_kinds[skip_self:]: |
| 1047 | self.fail( |
| 1048 | '"TypeIs" functions must have a positional argument', |
| 1049 | result, |
| 1050 | code=codes.VALID_TYPE, |
no test coverage detected