forked from VimPlug/jedi
Remove IsScope in favor of an is_scope function.
This function was partially implemented anway. Now we've also added a function called 'get_parent_scope', to make it easy to get a scope of a Call, Statement, whatever.
This commit is contained in:
@@ -360,7 +360,7 @@ class BaseDefinition(object):
|
|||||||
if isinstance(self._definition, compiled.CompiledObject):
|
if isinstance(self._definition, compiled.CompiledObject):
|
||||||
non_flow = self._definition.parent
|
non_flow = self._definition.parent
|
||||||
else:
|
else:
|
||||||
scope = self._definition.get_parent_until(pr.IsScope, include_current=False)
|
scope = self._definition.get_parent_scope(include_current=False)
|
||||||
non_flow = scope.get_parent_until(pr.Flow, reverse=True)
|
non_flow = scope.get_parent_until(pr.Flow, reverse=True)
|
||||||
return Definition(self._evaluator, non_flow)
|
return Definition(self._evaluator, non_flow)
|
||||||
|
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ def usages(evaluator, definitions, search_name, mods):
|
|||||||
|
|
||||||
def check_call_for_usage(call):
|
def check_call_for_usage(call):
|
||||||
stmt = call.parent
|
stmt = call.parent
|
||||||
while not isinstance(stmt.parent, pr.IsScope):
|
while not stmt.parent.is_scope():
|
||||||
stmt = stmt.parent
|
stmt = stmt.parent
|
||||||
# New definition, call cannot be a part of stmt
|
# New definition, call cannot be a part of stmt
|
||||||
if len(call.name) == 1 and call.execution is None \
|
if len(call.name) == 1 and call.execution is None \
|
||||||
|
|||||||
@@ -220,9 +220,10 @@ class Evaluator(object):
|
|||||||
"""Follow a call is following a function, variable, string, etc."""
|
"""Follow a call is following a function, variable, string, etc."""
|
||||||
path = call.generate_call_path()
|
path = call.generate_call_path()
|
||||||
|
|
||||||
|
# TODO use scope_parent
|
||||||
# find the statement of the Scope
|
# find the statement of the Scope
|
||||||
s = call
|
s = call
|
||||||
while not s.parent.isinstance(pr.IsScope):
|
while not s.parent.is_scope():
|
||||||
s = s.parent
|
s = s.parent
|
||||||
par = s.parent
|
par = s.parent
|
||||||
return self.eval_call_path(path, par, s.start_pos)
|
return self.eval_call_path(path, par, s.start_pos)
|
||||||
@@ -335,7 +336,7 @@ class Evaluator(object):
|
|||||||
return types
|
return types
|
||||||
|
|
||||||
def goto(self, stmt, call_path):
|
def goto(self, stmt, call_path):
|
||||||
scope = stmt.get_parent_until(pr.IsScope)
|
scope = stmt.get_parent_scope()
|
||||||
pos = stmt.start_pos
|
pos = stmt.start_pos
|
||||||
call_path, search_name_part = call_path[:-1], call_path[-1]
|
call_path, search_name_part = call_path[:-1], call_path[-1]
|
||||||
|
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ from jedi._compatibility import builtins as _builtins, unicode
|
|||||||
from jedi import debug
|
from jedi import debug
|
||||||
from jedi.cache import underscore_memoization, memoize
|
from jedi.cache import underscore_memoization, memoize
|
||||||
from jedi.evaluate.sys_path import get_sys_path
|
from jedi.evaluate.sys_path import get_sys_path
|
||||||
from jedi.parser.representation import Param, SubModule, Base, IsScope, Operator
|
from jedi.parser.representation import Param, SubModule, Base, Operator
|
||||||
from jedi.evaluate.helpers import FakeName
|
from jedi.evaluate.helpers import FakeName
|
||||||
from . import fake
|
from . import fake
|
||||||
|
|
||||||
@@ -374,12 +374,15 @@ def _parse_function_doc(doc):
|
|||||||
return param_str, ret
|
return param_str, ret
|
||||||
|
|
||||||
|
|
||||||
class Builtin(CompiledObject, IsScope):
|
class Builtin(CompiledObject, Base):
|
||||||
@memoize
|
@memoize
|
||||||
def get_by_name(self, name):
|
def get_by_name(self, name):
|
||||||
item = [n for n in self.get_defined_names() if n.get_code() == name][0]
|
item = [n for n in self.get_defined_names() if n.get_code() == name][0]
|
||||||
return item.parent
|
return item.parent
|
||||||
|
|
||||||
|
def is_scope(self):
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
def _a_generator(foo):
|
def _a_generator(foo):
|
||||||
"""Used to have an object to return for generators."""
|
"""Used to have an object to return for generators."""
|
||||||
|
|||||||
@@ -380,7 +380,7 @@ def check_flow_information(evaluator, flow, search_name_part, pos):
|
|||||||
return None
|
return None
|
||||||
|
|
||||||
result = []
|
result = []
|
||||||
if isinstance(flow, pr.IsScope):
|
if flow.is_scope():
|
||||||
for ass in reversed(flow.asserts):
|
for ass in reversed(flow.asserts):
|
||||||
if pos is None or ass.start_pos > pos:
|
if pos is None or ass.start_pos > pos:
|
||||||
continue
|
continue
|
||||||
|
|||||||
@@ -337,7 +337,7 @@ def _check_array_additions(evaluator, compare_array, module, is_list):
|
|||||||
backtrack_path = iter(call_path[:separate_index])
|
backtrack_path = iter(call_path[:separate_index])
|
||||||
|
|
||||||
position = c.start_pos
|
position = c.start_pos
|
||||||
scope = c.get_parent_until(pr.IsScope)
|
scope = c.get_parent_scope()
|
||||||
|
|
||||||
found = evaluator.eval_call_path(backtrack_path, scope, position)
|
found = evaluator.eval_call_path(backtrack_path, scope, position)
|
||||||
if not compare_array in found:
|
if not compare_array in found:
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ def wrap(evaluator, element):
|
|||||||
return element
|
return element
|
||||||
|
|
||||||
|
|
||||||
class Executed(pr.IsScope):
|
class Executed(pr.Base):
|
||||||
"""
|
"""
|
||||||
An instance is also an executable - because __init__ is called
|
An instance is also an executable - because __init__ is called
|
||||||
:param var_args: The param input array, consist of `pr.Array` or list.
|
:param var_args: The param input array, consist of `pr.Array` or list.
|
||||||
@@ -51,6 +51,9 @@ class Executed(pr.IsScope):
|
|||||||
self.base = base
|
self.base = base
|
||||||
self.var_args = var_args
|
self.var_args = var_args
|
||||||
|
|
||||||
|
def is_scope(self):
|
||||||
|
return True
|
||||||
|
|
||||||
def get_parent_until(self, *args, **kwargs):
|
def get_parent_until(self, *args, **kwargs):
|
||||||
return self.base.get_parent_until(*args, **kwargs)
|
return self.base.get_parent_until(*args, **kwargs)
|
||||||
|
|
||||||
@@ -278,6 +281,12 @@ class InstanceElement(use_metaclass(CachedMetaClass, pr.Base)):
|
|||||||
def isinstance(self, *cls):
|
def isinstance(self, *cls):
|
||||||
return isinstance(self.var, cls)
|
return isinstance(self.var, cls)
|
||||||
|
|
||||||
|
def is_scope(self):
|
||||||
|
"""
|
||||||
|
Since we inherit from Base, it would overwrite the action we want here.
|
||||||
|
"""
|
||||||
|
return self.var.is_scope()
|
||||||
|
|
||||||
def py__call__(self, evaluator, params):
|
def py__call__(self, evaluator, params):
|
||||||
return Function.py__call__(self, evaluator, params)
|
return Function.py__call__(self, evaluator, params)
|
||||||
|
|
||||||
@@ -285,7 +294,12 @@ class InstanceElement(use_metaclass(CachedMetaClass, pr.Base)):
|
|||||||
return "<%s of %s>" % (type(self).__name__, self.var)
|
return "<%s of %s>" % (type(self).__name__, self.var)
|
||||||
|
|
||||||
|
|
||||||
class Class(use_metaclass(CachedMetaClass, pr.IsScope)):
|
class Wrapper(pr.Base):
|
||||||
|
def is_scope(self):
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
|
class Class(use_metaclass(CachedMetaClass, Wrapper)):
|
||||||
"""
|
"""
|
||||||
This class is not only important to extend `pr.Class`, it is also a
|
This class is not only important to extend `pr.Class`, it is also a
|
||||||
important for descriptors (if the descriptor methods are evaluated or not).
|
important for descriptors (if the descriptor methods are evaluated or not).
|
||||||
@@ -376,7 +390,7 @@ class Class(use_metaclass(CachedMetaClass, pr.IsScope)):
|
|||||||
return "<e%s of %s>" % (type(self).__name__, self.base)
|
return "<e%s of %s>" % (type(self).__name__, self.base)
|
||||||
|
|
||||||
|
|
||||||
class Function(use_metaclass(CachedMetaClass, pr.IsScope)):
|
class Function(use_metaclass(CachedMetaClass, Wrapper)):
|
||||||
"""
|
"""
|
||||||
Needed because of decorators. Decorators are evaluated here.
|
Needed because of decorators. Decorators are evaluated here.
|
||||||
"""
|
"""
|
||||||
|
|||||||
@@ -134,11 +134,23 @@ class Base(object):
|
|||||||
classes = (classes,)
|
classes = (classes,)
|
||||||
scope = self if include_current else self.parent
|
scope = self if include_current else self.parent
|
||||||
while scope.parent is not None:
|
while scope.parent is not None:
|
||||||
|
# TODO why if classes?
|
||||||
if classes and reverse != scope.isinstance(*classes):
|
if classes and reverse != scope.isinstance(*classes):
|
||||||
break
|
break
|
||||||
scope = scope.parent
|
scope = scope.parent
|
||||||
return scope
|
return scope
|
||||||
|
|
||||||
|
def get_parent_scope(self, include_current=True):
|
||||||
|
"""
|
||||||
|
Returns the underlying scope.
|
||||||
|
"""
|
||||||
|
scope = self if include_current else self.parent
|
||||||
|
while scope.parent is not None:
|
||||||
|
if scope.is_scope():
|
||||||
|
break
|
||||||
|
scope = scope.parent
|
||||||
|
return scope
|
||||||
|
|
||||||
def space(self, from_pos, to_pos):
|
def space(self, from_pos, to_pos):
|
||||||
"""Return the space between two tokens"""
|
"""Return the space between two tokens"""
|
||||||
linecount = to_pos[0] - from_pos[0]
|
linecount = to_pos[0] - from_pos[0]
|
||||||
@@ -150,6 +162,10 @@ class Base(object):
|
|||||||
self.whitespace * to_pos[1],
|
self.whitespace * to_pos[1],
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def is_scope(self):
|
||||||
|
# Default is not being a scope. Just inherit from Scope.
|
||||||
|
return False
|
||||||
|
|
||||||
|
|
||||||
class Simple(Base):
|
class Simple(Base):
|
||||||
"""
|
"""
|
||||||
@@ -205,18 +221,8 @@ class Simple(Base):
|
|||||||
return "<%s: %s@%s,%s>" % \
|
return "<%s: %s@%s,%s>" % \
|
||||||
(type(self).__name__, code, self.start_pos[0], self.start_pos[1])
|
(type(self).__name__, code, self.start_pos[0], self.start_pos[1])
|
||||||
|
|
||||||
def is_scope(self):
|
|
||||||
return False
|
|
||||||
|
|
||||||
|
class Scope(Simple, DocstringMixin):
|
||||||
class IsScope(Base):
|
|
||||||
__slots__ = ()
|
|
||||||
|
|
||||||
def is_scope(self):
|
|
||||||
return True
|
|
||||||
|
|
||||||
|
|
||||||
class Scope(IsScope, Simple, DocstringMixin):
|
|
||||||
"""
|
"""
|
||||||
Super class for the parser tree, which represents the state of a python
|
Super class for the parser tree, which represents the state of a python
|
||||||
text file.
|
text file.
|
||||||
@@ -242,6 +248,9 @@ class Scope(IsScope, Simple, DocstringMixin):
|
|||||||
self.returns = []
|
self.returns = []
|
||||||
self.is_generator = False
|
self.is_generator = False
|
||||||
|
|
||||||
|
def is_scope(self):
|
||||||
|
return True
|
||||||
|
|
||||||
def add_scope(self, sub, decorators):
|
def add_scope(self, sub, decorators):
|
||||||
sub.parent = self.use_as_parent
|
sub.parent = self.use_as_parent
|
||||||
sub.decorators = decorators
|
sub.decorators = decorators
|
||||||
@@ -384,10 +393,12 @@ class Scope(IsScope, Simple, DocstringMixin):
|
|||||||
r = r.next
|
r = r.next
|
||||||
|
|
||||||
|
|
||||||
class Module(IsScope):
|
class Module(Base):
|
||||||
"""
|
"""
|
||||||
For isinstance checks. fast_parser.Module also inherits from this.
|
For isinstance checks. fast_parser.Module also inherits from this.
|
||||||
"""
|
"""
|
||||||
|
def is_scope(self):
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
class SubModule(Scope, Module):
|
class SubModule(Scope, Module):
|
||||||
@@ -846,9 +857,6 @@ class KeywordStatement(Base):
|
|||||||
if stmt is not None:
|
if stmt is not None:
|
||||||
stmt.parent = self
|
stmt.parent = self
|
||||||
|
|
||||||
def is_scope(self):
|
|
||||||
return False
|
|
||||||
|
|
||||||
def __repr__(self):
|
def __repr__(self):
|
||||||
return "<%s(%s): %s>" % (type(self).__name__, self.name, self.stmt)
|
return "<%s(%s): %s>" % (type(self).__name__, self.name, self.stmt)
|
||||||
|
|
||||||
@@ -1099,7 +1107,7 @@ class Statement(Simple, DocstringMixin):
|
|||||||
return None, tok
|
return None, tok
|
||||||
|
|
||||||
# Since Lambda is a Function scope, it needs Scope parents.
|
# Since Lambda is a Function scope, it needs Scope parents.
|
||||||
parent = self.get_parent_until(IsScope)
|
parent = self.get_parent_scope()
|
||||||
lambd = Lambda(self._sub_module, params, start_pos, parent)
|
lambd = Lambda(self._sub_module, params, start_pos, parent)
|
||||||
|
|
||||||
ret, tok = parse_stmt(token_iterator)
|
ret, tok = parse_stmt(token_iterator)
|
||||||
|
|||||||
Reference in New Issue
Block a user