Browse Source

Intermediate changes

robot-piglet 11 months ago
parent
commit
7930380b35

+ 5 - 3
contrib/python/ipython/py3/.dist-info/METADATA

@@ -1,6 +1,6 @@
 Metadata-Version: 2.1
 Name: ipython
-Version: 8.22.2
+Version: 8.23.0
 Summary: IPython: Productive Interactive Computing
 Author: The IPython Development Team
 Author-email: ipython-dev@python.org
@@ -33,12 +33,12 @@ Requires-Dist: prompt-toolkit <3.1.0,>=3.0.41
 Requires-Dist: pygments >=2.4.0
 Requires-Dist: stack-data
 Requires-Dist: traitlets >=5.13.0
-Requires-Dist: typing-extensions ; python_version < "3.10"
 Requires-Dist: exceptiongroup ; python_version < "3.11"
+Requires-Dist: typing-extensions ; python_version < "3.12"
 Requires-Dist: pexpect >4.3 ; sys_platform != "win32" and sys_platform != "emscripten"
 Requires-Dist: colorama ; sys_platform == "win32"
 Provides-Extra: all
-Requires-Dist: ipython[black,doc,kernel,nbconvert,nbformat,notebook,parallel,qtconsole,terminal] ; extra == 'all'
+Requires-Dist: ipython[black,doc,kernel,matplotlib,nbconvert,nbformat,notebook,parallel,qtconsole] ; extra == 'all'
 Requires-Dist: ipython[test,test_extra] ; extra == 'all'
 Provides-Extra: black
 Requires-Dist: black ; extra == 'black'
@@ -56,6 +56,8 @@ Requires-Dist: exceptiongroup ; extra == 'doc'
 Requires-Dist: ipython[test] ; extra == 'doc'
 Provides-Extra: kernel
 Requires-Dist: ipykernel ; extra == 'kernel'
+Provides-Extra: matplotlib
+Requires-Dist: matplotlib ; extra == 'matplotlib'
 Provides-Extra: nbconvert
 Requires-Dist: nbconvert ; extra == 'nbconvert'
 Provides-Extra: nbformat

+ 183 - 45
contrib/python/ipython/py3/IPython/core/guarded_eval.py

@@ -1,16 +1,23 @@
-from inspect import signature, Signature
+from inspect import isclass, signature, Signature
 from typing import (
-    Any,
+    Annotated,
+    AnyStr,
     Callable,
     Dict,
+    Literal,
+    NamedTuple,
+    NewType,
+    Optional,
+    Protocol,
     Set,
     Sequence,
     Tuple,
-    NamedTuple,
     Type,
-    Literal,
+    TypeGuard,
     Union,
-    TYPE_CHECKING,
+    get_args,
+    get_origin,
+    is_typeddict,
 )
 import ast
 import builtins
@@ -21,15 +28,18 @@ from functools import cached_property
 from dataclasses import dataclass, field
 from types import MethodDescriptorType, ModuleType
 
-from IPython.utils.docs import GENERATING_DOCUMENTATION
 from IPython.utils.decorators import undoc
 
 
-if TYPE_CHECKING or GENERATING_DOCUMENTATION:
-    from typing_extensions import Protocol
+if sys.version_info < (3, 11):
+    from typing_extensions import Self, LiteralString
+else:
+    from typing import Self, LiteralString
+
+if sys.version_info < (3, 12):
+    from typing_extensions import TypeAliasType
 else:
-    # do not require on runtime
-    Protocol = object  # requires Python >=3.8
+    from typing import TypeAliasType
 
 
 @undoc
@@ -337,6 +347,7 @@ class _IdentitySubscript:
 IDENTITY_SUBSCRIPT = _IdentitySubscript()
 SUBSCRIPT_MARKER = "__SUBSCRIPT_SENTINEL__"
 UNKNOWN_SIGNATURE = Signature()
+NOT_EVALUATED = object()
 
 
 class GuardRejection(Exception):
@@ -417,9 +428,37 @@ UNARY_OP_DUNDERS: Dict[Type[ast.unaryop], Tuple[str, ...]] = {
 }
 
 
-class Duck:
+class ImpersonatingDuck:
     """A dummy class used to create objects of other classes without calling their ``__init__``"""
 
+    # no-op: override __class__ to impersonate
+
+
+class _Duck:
+    """A dummy class used to create objects pretending to have given attributes"""
+
+    def __init__(self, attributes: Optional[dict] = None, items: Optional[dict] = None):
+        self.attributes = attributes or {}
+        self.items = items or {}
+
+    def __getattr__(self, attr: str):
+        return self.attributes[attr]
+
+    def __hasattr__(self, attr: str):
+        return attr in self.attributes
+
+    def __dir__(self):
+        return [*dir(super), *self.attributes]
+
+    def __getitem__(self, key: str):
+        return self.items[key]
+
+    def __hasitem__(self, key: str):
+        return self.items[key]
+
+    def _ipython_key_completions_(self):
+        return self.items.keys()
+
 
 def _find_dunder(node_op, dunders) -> Union[Tuple[str, ...], None]:
     dunder = None
@@ -557,19 +596,7 @@ def eval_node(node: Union[ast.AST, None], context: EvaluationContext):
             f" not allowed in {context.evaluation} mode",
         )
     if isinstance(node, ast.Name):
-        if policy.allow_locals_access and node.id in context.locals:
-            return context.locals[node.id]
-        if policy.allow_globals_access and node.id in context.globals:
-            return context.globals[node.id]
-        if policy.allow_builtins_access and hasattr(builtins, node.id):
-            # note: do not use __builtins__, it is implementation detail of cPython
-            return getattr(builtins, node.id)
-        if not policy.allow_globals_access and not policy.allow_locals_access:
-            raise GuardRejection(
-                f"Namespace access not allowed in {context.evaluation} mode"
-            )
-        else:
-            raise NameError(f"{node.id} not found in locals, globals, nor builtins")
+        return _eval_node_name(node.id, context)
     if isinstance(node, ast.Attribute):
         value = eval_node(node.value, context)
         if policy.can_get_attr(value, node.attr):
@@ -590,27 +617,19 @@ def eval_node(node: Union[ast.AST, None], context: EvaluationContext):
         if policy.can_call(func) and not node.keywords:
             args = [eval_node(arg, context) for arg in node.args]
             return func(*args)
-        try:
-            sig = signature(func)
-        except ValueError:
-            sig = UNKNOWN_SIGNATURE
-        # if annotation was not stringized, or it was stringized
-        # but resolved by signature call we know the return type
-        not_empty = sig.return_annotation is not Signature.empty
-        not_stringized = not isinstance(sig.return_annotation, str)
-        if not_empty and not_stringized:
-            duck = Duck()
-            # if allow-listed builtin is on type annotation, instantiate it
-            if policy.can_call(sig.return_annotation) and not node.keywords:
-                args = [eval_node(arg, context) for arg in node.args]
-                return sig.return_annotation(*args)
-            try:
-                # if custom class is in type annotation, mock it;
-                # this only works for heap types, not builtins
-                duck.__class__ = sig.return_annotation
-                return duck
-            except TypeError:
-                pass
+        if isclass(func):
+            # this code path gets entered when calling class e.g. `MyClass()`
+            # or `my_instance.__class__()` - in both cases `func` is `MyClass`.
+            # Should return `MyClass` if `__new__` is not overridden,
+            # otherwise whatever `__new__` return type is.
+            overridden_return_type = _eval_return_type(func.__new__, node, context)
+            if overridden_return_type is not NOT_EVALUATED:
+                return overridden_return_type
+            return _create_duck_for_heap_type(func)
+        else:
+            return_type = _eval_return_type(func, node, context)
+            if return_type is not NOT_EVALUATED:
+                return return_type
         raise GuardRejection(
             "Call for",
             func,  # not joined to avoid calling `repr`
@@ -619,6 +638,125 @@ def eval_node(node: Union[ast.AST, None], context: EvaluationContext):
     raise ValueError("Unhandled node", ast.dump(node))
 
 
+def _eval_return_type(func: Callable, node: ast.Call, context: EvaluationContext):
+    """Evaluate return type of a given callable function.
+
+    Returns the built-in type, a duck or NOT_EVALUATED sentinel.
+    """
+    try:
+        sig = signature(func)
+    except ValueError:
+        sig = UNKNOWN_SIGNATURE
+    # if annotation was not stringized, or it was stringized
+    # but resolved by signature call we know the return type
+    not_empty = sig.return_annotation is not Signature.empty
+    if not_empty:
+        return _resolve_annotation(sig.return_annotation, sig, func, node, context)
+    return NOT_EVALUATED
+
+
+def _resolve_annotation(
+    annotation,
+    sig: Signature,
+    func: Callable,
+    node: ast.Call,
+    context: EvaluationContext,
+):
+    """Resolve annotation created by user with `typing` module and custom objects."""
+    annotation = (
+        _eval_node_name(annotation, context)
+        if isinstance(annotation, str)
+        else annotation
+    )
+    origin = get_origin(annotation)
+    if annotation is Self and hasattr(func, "__self__"):
+        return func.__self__
+    elif origin is Literal:
+        type_args = get_args(annotation)
+        if len(type_args) == 1:
+            return type_args[0]
+    elif annotation is LiteralString:
+        return ""
+    elif annotation is AnyStr:
+        index = None
+        for i, (key, value) in enumerate(sig.parameters.items()):
+            if value.annotation is AnyStr:
+                index = i
+                break
+        if index is not None and index < len(node.args):
+            return eval_node(node.args[index], context)
+    elif origin is TypeGuard:
+        return bool()
+    elif origin is Union:
+        attributes = [
+            attr
+            for type_arg in get_args(annotation)
+            for attr in dir(_resolve_annotation(type_arg, sig, func, node, context))
+        ]
+        return _Duck(attributes=dict.fromkeys(attributes))
+    elif is_typeddict(annotation):
+        return _Duck(
+            attributes=dict.fromkeys(dir(dict())),
+            items={
+                k: _resolve_annotation(v, sig, func, node, context)
+                for k, v in annotation.__annotations__.items()
+            },
+        )
+    elif hasattr(annotation, "_is_protocol"):
+        return _Duck(attributes=dict.fromkeys(dir(annotation)))
+    elif origin is Annotated:
+        type_arg = get_args(annotation)[0]
+        return _resolve_annotation(type_arg, sig, func, node, context)
+    elif isinstance(annotation, NewType):
+        return _eval_or_create_duck(annotation.__supertype__, node, context)
+    elif isinstance(annotation, TypeAliasType):
+        return _eval_or_create_duck(annotation.__value__, node, context)
+    else:
+        return _eval_or_create_duck(annotation, node, context)
+
+
+def _eval_node_name(node_id: str, context: EvaluationContext):
+    policy = EVALUATION_POLICIES[context.evaluation]
+    if policy.allow_locals_access and node_id in context.locals:
+        return context.locals[node_id]
+    if policy.allow_globals_access and node_id in context.globals:
+        return context.globals[node_id]
+    if policy.allow_builtins_access and hasattr(builtins, node_id):
+        # note: do not use __builtins__, it is implementation detail of cPython
+        return getattr(builtins, node_id)
+    if not policy.allow_globals_access and not policy.allow_locals_access:
+        raise GuardRejection(
+            f"Namespace access not allowed in {context.evaluation} mode"
+        )
+    else:
+        raise NameError(f"{node_id} not found in locals, globals, nor builtins")
+
+
+def _eval_or_create_duck(duck_type, node: ast.Call, context: EvaluationContext):
+    policy = EVALUATION_POLICIES[context.evaluation]
+    # if allow-listed builtin is on type annotation, instantiate it
+    if policy.can_call(duck_type) and not node.keywords:
+        args = [eval_node(arg, context) for arg in node.args]
+        return duck_type(*args)
+    # if custom class is in type annotation, mock it
+    return _create_duck_for_heap_type(duck_type)
+
+
+def _create_duck_for_heap_type(duck_type):
+    """Create an imitation of an object of a given type (a duck).
+
+    Returns the duck or NOT_EVALUATED sentinel if duck could not be created.
+    """
+    duck = ImpersonatingDuck()
+    try:
+        # this only works for heap types, not builtins
+        duck.__class__ = duck_type
+        return duck
+    except TypeError:
+        pass
+    return NOT_EVALUATED
+
+
 SUPPORTED_EXTERNAL_GETITEM = {
     ("pandas", "core", "indexing", "_iLocIndexer"),
     ("pandas", "core", "indexing", "_LocIndexer"),

+ 3 - 0
contrib/python/ipython/py3/IPython/core/magics/basic.py

@@ -40,6 +40,9 @@ class MagicsDisplay(object):
     def _repr_pretty_(self, p, cycle):
         p.text(self._lsmagic())
     
+    def __repr__(self):
+        return self.__str__()
+
     def __str__(self):
         return self._lsmagic()
     

+ 1 - 1
contrib/python/ipython/py3/IPython/core/magics/execution.py

@@ -1506,7 +1506,7 @@ class ExecutionMagics(Magics):
     @line_cell_magic
     def code_wrap(self, line, cell=None):
         """
-        Simple magic to quickly define a code transformer for all IPython's future imput.
+        Simple magic to quickly define a code transformer for all IPython's future input.
 
         ``__code__`` and ``__ret__`` are special variable that represent the code to run
         and the value of the last expression of ``__code__`` respectively.

+ 2 - 2
contrib/python/ipython/py3/IPython/core/release.py

@@ -16,8 +16,8 @@
 # release.  'dev' as a _version_extra string means this is a development
 # version
 _version_major = 8
-_version_minor = 22
-_version_patch = 2
+_version_minor = 23
+_version_patch = 0
 _version_extra = ".dev"
 # _version_extra = "rc1"
 _version_extra = ""  # Uncomment this for full releases

+ 1 - 1
contrib/python/ipython/py3/IPython/utils/_sysinfo.py

@@ -1,2 +1,2 @@
 # GENERATED BY setup.py
-commit = "d1804576b"
+commit = "5e7c4a991"

+ 1 - 1
contrib/python/ipython/py3/ya.make

@@ -2,7 +2,7 @@
 
 PY3_LIBRARY()
 
-VERSION(8.22.2)
+VERSION(8.23.0)
 
 LICENSE(BSD-3-Clause)
 

+ 11 - 14
contrib/python/pycparser/py3/.dist-info/METADATA

@@ -1,31 +1,28 @@
 Metadata-Version: 2.1
 Name: pycparser
-Version: 2.21
+Version: 2.22
 Summary: C parser in Python
 Home-page: https://github.com/eliben/pycparser
 Author: Eli Bendersky
 Author-email: eliben@gmail.com
 Maintainer: Eli Bendersky
-License: BSD
+License: BSD-3-Clause
 Platform: Cross Platform
 Classifier: Development Status :: 5 - Production/Stable
 Classifier: License :: OSI Approved :: BSD License
-Classifier: Programming Language :: Python :: 2
-Classifier: Programming Language :: Python :: 2.7
 Classifier: Programming Language :: Python :: 3
-Classifier: Programming Language :: Python :: 3.4
-Classifier: Programming Language :: Python :: 3.5
-Classifier: Programming Language :: Python :: 3.6
-Classifier: Programming Language :: Python :: 3.7
 Classifier: Programming Language :: Python :: 3.8
 Classifier: Programming Language :: Python :: 3.9
 Classifier: Programming Language :: Python :: 3.10
-Requires-Python: >=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*
+Classifier: Programming Language :: Python :: 3.11
+Classifier: Programming Language :: Python :: 3.12
+Requires-Python: >=3.8
+License-File: LICENSE
 
 
-pycparser is a complete parser of the C language, written in
-pure Python using the PLY parsing library.
-It parses C code into an AST and can serve as a front-end for
-C compilers or analysis tools.
-
+        pycparser is a complete parser of the C language, written in
+        pure Python using the PLY parsing library.
+        It parses C code into an AST and can serve as a front-end for
+        C compilers or analysis tools.
+    
 

+ 2 - 2
contrib/python/pycparser/py3/LICENSE

@@ -1,6 +1,6 @@
 pycparser -- A C parser in Python
 
-Copyright (c) 2008-2020, Eli Bendersky
+Copyright (c) 2008-2022, Eli Bendersky
 All rights reserved.
 
 Redistribution and use in source and binary forms, with or without modification,
@@ -11,7 +11,7 @@ are permitted provided that the following conditions are met:
 * Redistributions in binary form must reproduce the above copyright notice, 
   this list of conditions and the following disclaimer in the documentation 
   and/or other materials provided with the distribution.
-* Neither the name of Eli Bendersky nor the names of its contributors may 
+* Neither the name of the copyright holder nor the names of its contributors may 
   be used to endorse or promote products derived from this software without 
   specific prior written permission.
 

+ 3 - 23
contrib/python/pycparser/py3/README.rst

@@ -1,5 +1,5 @@
 ===============
-pycparser v2.21
+pycparser v2.22
 ===============
 
 
@@ -83,9 +83,7 @@ Installing
 Prerequisites
 -------------
 
-* **pycparser** was tested on Python 2.7, 3.4-3.6, on both Linux and
-  Windows. It should work on any later version (in both the 2.x and 3.x lines)
-  as well.
+* **pycparser** was tested with Python 3.8+ on Linux, macOS and Windows.
 
 * **pycparser** has no external dependencies. The only non-stdlib library it
   uses is PLY, which is bundled in ``pycparser/ply``. The current PLY version is
@@ -101,28 +99,10 @@ though.
 Installation process
 --------------------
 
-Installing **pycparser** is very simple. Once you download and unzip the
-package, you just have to execute the standard ``python setup.py install``. The
-setup script will then place the ``pycparser`` module into ``site-packages`` in
-your Python's installation library.
-
-Alternatively, since **pycparser** is listed in the `Python Package Index
-<https://pypi.org/project/pycparser/>`_ (PyPI), you can install it using your
-favorite Python packaging/distribution tool, for example with::
+The recommended way to install **pycparser** is with ``pip``::
 
     > pip install pycparser
 
-Known problems
---------------
-
-* Some users who've installed a new version of **pycparser** over an existing
-  version ran into a problem using the newly installed library. This has to do
-  with parse tables staying around as ``.pyc`` files from the older version. If
-  you see unexplained errors from **pycparser** after an upgrade, remove it (by
-  deleting the ``pycparser`` directory in your Python's ``site-packages``, or
-  wherever you installed it) and install again.
-
-
 Using
 =====
 

Some files were not shown because too many files changed in this diff