mirror of
https://github.com/davidhalter/jedi.git
synced 2025-12-06 22:14:27 +08:00
Dataclass progress
This commit is contained in:
@@ -140,3 +140,11 @@ def skip_pre_python38(environment):
|
||||
# This if is just needed to avoid that tests ever skip way more than
|
||||
# they should for all Python versions.
|
||||
pytest.skip()
|
||||
|
||||
|
||||
@pytest.fixture()
|
||||
def skip_pre_python37(environment):
|
||||
if environment.version_info < (3, 7):
|
||||
# This if is just needed to avoid that tests ever skip way more than
|
||||
# they should for all Python versions.
|
||||
pytest.skip()
|
||||
|
||||
@@ -198,12 +198,7 @@ class ClassMixin(object):
|
||||
yield f
|
||||
|
||||
if search_global:
|
||||
yield ParserTreeFilter(
|
||||
self.evaluator,
|
||||
context=self,
|
||||
until_position=until_position,
|
||||
origin_scope=origin_scope
|
||||
)
|
||||
yield self.get_global_filter(until_position, origin_scope)
|
||||
else:
|
||||
for cls in self.py__mro__():
|
||||
if isinstance(cls, compiled.CompiledObject):
|
||||
@@ -227,6 +222,14 @@ class ClassMixin(object):
|
||||
next(instance_filters)
|
||||
yield next(instance_filters)
|
||||
|
||||
def get_global_filter(self, until_position=None, origin_scope=None):
|
||||
return ParserTreeFilter(
|
||||
self.evaluator,
|
||||
context=self,
|
||||
until_position=until_position,
|
||||
origin_scope=origin_scope
|
||||
)
|
||||
|
||||
|
||||
class ClassContext(use_metaclass(CachedMetaClass, ClassMixin, FunctionAndClassBase)):
|
||||
"""
|
||||
|
||||
@@ -520,6 +520,37 @@ def _random_choice(sequences):
|
||||
)
|
||||
|
||||
|
||||
def _dataclass(obj, arguments):
|
||||
for c in _follow_param(obj.evaluator, arguments, 0):
|
||||
if c.is_class():
|
||||
return ContextSet([DataclassWrapper(c)])
|
||||
else:
|
||||
return ContextSet([obj])
|
||||
return NO_CONTEXTS
|
||||
|
||||
|
||||
class DataclassWrapper(ContextWrapper):
|
||||
def get_signatures(self):
|
||||
params = []
|
||||
for cls in reversed(self._wrapped_context.py__mro__()):
|
||||
if isinstance(cls, ClassContext) and not cls.is_stub():
|
||||
filter_ = cls.get_global_filter()
|
||||
print(filter_)
|
||||
for name in filter_.values():
|
||||
d = name.tree_name.get_definition()
|
||||
if d.type == 'expr_stmt' and d.children[1].type == 'annassign':
|
||||
params.append()
|
||||
return [DataclassSignature(cls, params)]
|
||||
|
||||
|
||||
class DataclassSignature(AbstractSignature):
|
||||
def __init__(self, context, params):
|
||||
super(DataclassSignature, self).__init__(context)
|
||||
self._params = params
|
||||
|
||||
def get_param_names(self):
|
||||
|
||||
|
||||
class ItemGetterCallable(ContextWrapper):
|
||||
def __init__(self, instance, args_context_set):
|
||||
super(ItemGetterCallable, self).__init__(instance)
|
||||
@@ -602,7 +633,7 @@ _implemented = {
|
||||
},
|
||||
'dataclasses': {
|
||||
# For now this works at least better than Jedi trying to understand it.
|
||||
'dataclass': lambda obj, arguments: NO_CONTEXTS,
|
||||
'dataclass': _dataclass
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
import pytest
|
||||
from textwrap import dedent
|
||||
from operator import ge, lt
|
||||
|
||||
import pytest
|
||||
|
||||
from jedi.evaluate.gradual.conversion import _stub_to_python_context_set
|
||||
|
||||
|
||||
@@ -60,3 +62,20 @@ def test_pow_signature(Script):
|
||||
'pow(x: float, y: float, /) -> float',
|
||||
'pow(x: int, y: int, z: int, /) -> Any',
|
||||
'pow(x: int, y: int, /) -> Any'}
|
||||
|
||||
|
||||
@pytest.mark.parametrize('decorator', ['@dataclass', '@dataclass(eq=True)'])
|
||||
def test_dataclass_signature(Script, skip_pre_python37, decorator):
|
||||
code = dedent('''
|
||||
class InventoryItem:
|
||||
name: str
|
||||
foo = 3
|
||||
unit_price: float
|
||||
quantity_on_hand: int = 0
|
||||
|
||||
InventoryItem(''')
|
||||
|
||||
code = 'from dataclasses import dataclass\n' + decorator + code
|
||||
|
||||
sig, = Script(code).call_signatures()
|
||||
assert [p.name for p in sig.params] == ['name', 'unit_price', 'quantity_on_hand']
|
||||
|
||||
Reference in New Issue
Block a user