diff --git a/jedi/evaluate/base_context.py b/jedi/evaluate/base_context.py index ca2e074c..19df52ea 100644 --- a/jedi/evaluate/base_context.py +++ b/jedi/evaluate/base_context.py @@ -33,26 +33,14 @@ class Context(BaseContext): # overwritten. return self.__class__.__name__.lower() - @debug.increase_indent - def execute(self, arguments): - """ - In contrast to py__call__ this function is always available. - - `hasattr(x, py__call__)` can also be checked to see if a context is - executable. - """ - if self.evaluator.is_analysis: - arguments.eval_all() - - return self.evaluator.execute(self, arguments) - def execute_evaluated(self, *value_list): """ Execute a function with already executed arguments. """ + # TODO move this out of here to the evaluator. from jedi.evaluate.arguments import ValuesArguments arguments = ValuesArguments([ContextSet(value) for value in value_list]) - return self.execute(arguments) + return self.evaluator.execute(self, arguments) def iterate(self, contextualized_node=None, is_async=False): debug.dbg('iterate %s', self) @@ -248,6 +236,9 @@ class ContextSet(BaseContextSet): [l for l in lazy_contexts if l is not None] ) + def execute(self, arguments): + return ContextSet.from_sets(c.evaluator.execute(c, arguments) for c in self._set) + NO_CONTEXTS = ContextSet() diff --git a/jedi/evaluate/compiled/context.py b/jedi/evaluate/compiled/context.py index 2b87e3b1..3950aff8 100644 --- a/jedi/evaluate/compiled/context.py +++ b/jedi/evaluate/compiled/context.py @@ -187,7 +187,7 @@ class CompiledObject(Context): continue else: bltn_obj = builtin_from_name(self.evaluator, name) - for result in bltn_obj.execute(params): + for result in self.evaluator.execute(bltn_obj, params): yield result for type_ in docstrings.infer_return_types(self): yield type_ diff --git a/jedi/evaluate/context/instance.py b/jedi/evaluate/context/instance.py index def5e19a..f6fc344a 100644 --- a/jedi/evaluate/context/instance.py +++ b/jedi/evaluate/context/instance.py @@ -63,7 +63,7 @@ class AbstractInstanceContext(Context): raise AttributeError def execute(arguments): - return ContextSet.from_sets(name.execute(arguments) for name in names) + return ContextSet.from_sets(name.infer().execute(arguments) for name in names) return execute diff --git a/jedi/plugins/typeshed.py b/jedi/plugins/typeshed.py index 0126e7e4..6091642a 100644 --- a/jedi/plugins/typeshed.py +++ b/jedi/plugins/typeshed.py @@ -5,7 +5,7 @@ from pkg_resources import resource_filename from jedi._compatibility import FileNotFoundError from jedi.plugins.base import BasePlugin from jedi.evaluate.cache import evaluator_as_method_param_cache -from jedi.evaluate.base_context import Context, ContextSet +from jedi.evaluate.base_context import Context, ContextSet, NO_CONTEXTS from jedi.evaluate.context import ModuleContext @@ -19,7 +19,8 @@ def _create_stub_map(directory): def generate(): try: listed = os.listdir(directory) - except FileNotFoundError: + except (FileNotFoundError, OSError): + # OSError is Python 2 return for entry in listed: @@ -85,7 +86,7 @@ class TypeshedPlugin(BasePlugin): # ``os``. mapped = self._cache_stub_file_map(evaluator.grammar.version_info) context_set = callback(evaluator, import_names, module_context, sys_path) - if len(import_names) == 1: + if len(import_names) == 1 and import_names[0] != 'typing': path = mapped.get(import_names[0]) if path is not None: try: @@ -119,15 +120,25 @@ class StubProxy(object): context_results = self._context.py__getattribute__( *args, **kwargs ) - typeshed_results = self._stub_context.py__getattribute__( + typeshed_results = list(self._stub_context.py__getattribute__( *args, **kwargs + )) + if not typeshed_results: + return NO_CONTEXTS + + return ContextSet.from_iterable( + StubProxy(c.parent_context, c, typeshed_results[0]) for c in context_results ) - print() - print(context_results, typeshed_results) - return context_results + + @property + def py__call__(self): + def py__call__(arguments): + return self._stub_context.py__call__(arguments) + + return py__call__ def __getattr__(self, name): return getattr(self._context, name) def __repr__(self): - return '<%s: %s>' % (type(self).__name__, self.access_handle.get_repr()) + return '<%s: %s %s>' % (type(self).__name__, self._context, self._stub_context)