A first working iteration of dataclass signatures, fixes #1213

This commit is contained in:
Dave Halter
2019-07-19 02:01:36 +02:00
parent 7156ddf607
commit 050d686a27
2 changed files with 65 additions and 23 deletions

View File

@@ -168,14 +168,34 @@ class ParamNameInterface(object):
raise NotImplementedError raise NotImplementedError
class ParamName(ParamNameInterface, AbstractTreeName): class BaseTreeParamName(ParamNameInterface, AbstractTreeName):
def __init__(self, parent_context, tree_name): def get_default_node(self):
self.parent_context = parent_context return None
self.tree_name = tree_name
def get_annotation_node(self):
return None
def to_string(self):
output = self._kind_string() + self.string_name
annotation = self.get_annotation_node()
default = self.get_default_node()
if annotation is not None:
output += ': ' + annotation.get_code(include_prefix=False)
if default is not None:
output += '=' + default.get_code(include_prefix=False)
return output
class ParamName(BaseTreeParamName):
def _get_param_node(self): def _get_param_node(self):
return search_ancestor(self.tree_name, 'param') return search_ancestor(self.tree_name, 'param')
def get_annotation_node(self):
return self._get_param_node().annotation
def get_default_node(self):
return self._get_param_node().default
@property @property
def string_name(self): def string_name(self):
name = self.tree_name.value name = self.tree_name.value
@@ -213,15 +233,6 @@ class ParamName(ParamNameInterface, AbstractTreeName):
param_appeared = True param_appeared = True
return Parameter.POSITIONAL_OR_KEYWORD return Parameter.POSITIONAL_OR_KEYWORD
def to_string(self):
output = self._kind_string() + self.string_name
param_node = self._get_param_node()
if param_node.annotation is not None:
output += ': ' + param_node.annotation.get_code(include_prefix=False)
if param_node.default is not None:
output += '=' + param_node.default.get_code(include_prefix=False)
return output
def infer(self): def infer(self):
return self.get_param().infer() return self.get_param().infer()

View File

@@ -11,7 +11,7 @@ compiled module that returns the types for C-builtins.
""" """
import parso import parso
from jedi._compatibility import force_unicode from jedi._compatibility import force_unicode, Parameter
from jedi import debug from jedi import debug
from jedi.evaluate.utils import safe_property from jedi.evaluate.utils import safe_property
from jedi.evaluate.helpers import get_str_or_none from jedi.evaluate.helpers import get_str_or_none
@@ -27,10 +27,11 @@ from jedi.evaluate.context import ClassContext, ModuleContext, \
from jedi.evaluate.context import iterable from jedi.evaluate.context import iterable
from jedi.evaluate.lazy_context import LazyTreeContext, LazyKnownContext, \ from jedi.evaluate.lazy_context import LazyTreeContext, LazyKnownContext, \
LazyKnownContexts LazyKnownContexts
from jedi.evaluate.names import ContextName from jedi.evaluate.names import ContextName, BaseTreeParamName
from jedi.evaluate.syntax_tree import is_string from jedi.evaluate.syntax_tree import is_string
from jedi.evaluate.filters import AttributeOverwrite, publish_method, \ from jedi.evaluate.filters import AttributeOverwrite, publish_method, \
ParserTreeFilter, DictFilter ParserTreeFilter, DictFilter
from jedi.evaluate.signature import AbstractSignature
# Copied from Python 3.6's stdlib. # Copied from Python 3.6's stdlib.
@@ -531,24 +532,54 @@ def _dataclass(obj, arguments):
class DataclassWrapper(ContextWrapper): class DataclassWrapper(ContextWrapper):
def get_signatures(self): def get_signatures(self):
params = [] param_names = []
for cls in reversed(self._wrapped_context.py__mro__()): for cls in reversed(list(self._wrapped_context.py__mro__())):
if isinstance(cls, ClassContext) and not cls.is_stub(): if isinstance(cls, ClassContext) and not cls.is_stub():
filter_ = cls.get_global_filter() filter_ = cls.get_global_filter()
print(filter_)
for name in filter_.values(): for name in filter_.values():
d = name.tree_name.get_definition() d = name.tree_name.get_definition()
if d.type == 'expr_stmt' and d.children[1].type == 'annassign': annassign = d.children[1]
params.append() if d.type == 'expr_stmt' and annassign.type == 'annassign':
return [DataclassSignature(cls, params)] if len(annassign.children) < 4:
default = None
else:
default = annassign.children[3]
param_names.append(DataclassParamName(
parent_context=cls.parent_context,
tree_name=name.tree_name,
annotation_node=annassign.children[1],
default_node=default,
))
return [DataclassSignature(cls, param_names)]
class DataclassSignature(AbstractSignature): class DataclassSignature(AbstractSignature):
def __init__(self, context, params): def __init__(self, context, param_names):
super(DataclassSignature, self).__init__(context) super(DataclassSignature, self).__init__(context)
self._params = params self._param_names = param_names
def get_param_names(self): def get_param_names(self):
return self._param_names
class DataclassParamName(BaseTreeParamName):
def __init__(self, parent_context, tree_name, annotation_node, default_node):
super(DataclassParamName, self).__init__(parent_context, tree_name)
self._annotation_node = annotation_node
self._default_node = default_node
def get_kind(self):
return Parameter.POSITIONAL_OR_KEYWORD
#TODO get_param?
def get_annotation_node(self):
return self._annotation_node
def get_default_node(self):
return self._default_node
def infer(self):
return NO_CONTEXTS # TODO implement
class ItemGetterCallable(ContextWrapper): class ItemGetterCallable(ContextWrapper):