@@ -73,7 +73,9 @@ def _extract_namedtuple_arg_or_keyword( # pylint: disable=inconsistent-return-s
73
73
74
74
def infer_func_form (
75
75
node : nodes .Call ,
76
- base_type : list [nodes .NodeNG ],
76
+ base_type : nodes .NodeNG ,
77
+ * ,
78
+ parent : nodes .NodeNG ,
77
79
context : InferenceContext | None = None ,
78
80
enum : bool = False ,
79
81
) -> tuple [nodes .ClassDef , str , list [str ]]:
@@ -146,15 +148,11 @@ def infer_func_form(
146
148
col_offset = node .col_offset ,
147
149
end_lineno = node .end_lineno ,
148
150
end_col_offset = node .end_col_offset ,
149
- parent = nodes . Unknown () ,
151
+ parent = parent ,
150
152
)
151
- # A typical ClassDef automatically adds its name to the parent scope,
152
- # but doing so causes problems, so defer setting parent until after init
153
- # see: https://github.com/pylint-dev/pylint/issues/5982
154
- class_node .parent = node .parent
155
153
class_node .postinit (
156
154
# set base class=tuple
157
- bases = base_type ,
155
+ bases = [ base_type ] ,
158
156
body = [],
159
157
decorators = None ,
160
158
)
@@ -194,25 +192,18 @@ def infer_named_tuple(
194
192
node : nodes .Call , context : InferenceContext | None = None
195
193
) -> Iterator [nodes .ClassDef ]:
196
194
"""Specific inference function for namedtuple Call node."""
197
- tuple_base_name : list [nodes .NodeNG ] = [
198
- nodes .Name (
199
- name = "tuple" ,
200
- parent = node .root (),
201
- lineno = 0 ,
202
- col_offset = 0 ,
203
- end_lineno = None ,
204
- end_col_offset = None ,
205
- )
206
- ]
195
+ tuple_base = util .safe_infer (_extract_single_node ("tuple" ))
196
+ assert isinstance (tuple_base , nodes .NodeNG )
197
+
207
198
class_node , name , attributes = infer_func_form (
208
- node , tuple_base_name , context = context
199
+ node , tuple_base , parent = AstroidManager (). adhoc_module , context = context
209
200
)
201
+
210
202
call_site = arguments .CallSite .from_call (node , context = context )
211
- node = extract_node ("import collections; collections.namedtuple" )
212
- try :
213
- func = next (node .infer ())
214
- except StopIteration as e :
215
- raise InferenceError (node = node ) from e
203
+ func = util .safe_infer (
204
+ _extract_single_node ("import collections; collections.namedtuple" )
205
+ )
206
+ assert isinstance (func , nodes .NodeNG )
216
207
try :
217
208
rename = next (
218
209
call_site .infer_argument (func , "rename" , context or InferenceContext ())
@@ -363,7 +354,17 @@ def value(self):
363
354
__members__ = ['']
364
355
"""
365
356
)
366
- class_node = infer_func_form (node , [enum_meta ], context = context , enum = True )[0 ]
357
+
358
+ # FIXME arguably, the base here shouldn't be the EnumMeta class definition
359
+ # itself, but a reference (Name) to it. Otherwise, the invariant that all
360
+ # children of a node have that node as their parent is broken.
361
+ class_node = infer_func_form (
362
+ node ,
363
+ enum_meta ,
364
+ parent = AstroidManager ().adhoc_module ,
365
+ context = context ,
366
+ enum = True ,
367
+ )[0 ]
367
368
return iter ([class_node .instantiate_class ()])
368
369
369
370
0 commit comments