Script 'mail_helper' called by obssrc
Hello community,
here is the log from the commit of package python-decorator for
openSUSE:Factory checked in at 2021-10-20 20:23:30
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-decorator (Old)
and /work/SRC/openSUSE:Factory/.python-decorator.new.1890 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "python-decorator"
Wed Oct 20 20:23:30 2021 rev:24 rq:925751 version:5.1.0
Changes:
--------
--- /work/SRC/openSUSE:Factory/python-decorator/python-decorator.changes
2021-08-11 11:47:01.369760525 +0200
+++
/work/SRC/openSUSE:Factory/.python-decorator.new.1890/python-decorator.changes
2021-10-20 20:24:17.169378144 +0200
@@ -1,0 +2,12 @@
+Sat Oct 16 20:56:50 UTC 2021 - Dirk M??ller <[email protected]>
+
+- update to 5.1.0:
+ * Added a function `decoratorx` using the `FunctionMaker` and thus
+ preserving the signature of `__code__` objects.
+ * Sphinx was printing a few warnings when building the documentation
+ * functions decorated with `decorator.contextmanager` were one-shot,
+ as discovered by Alex Pizarro.
+ * `decorator.decorator` was not passing the kwsyntax argument.
+- drop kwsyntax.patch (usptream)
+
+-------------------------------------------------------------------
Old:
----
decorator-5.0.9.tar.gz
kwsyntax.patch
New:
----
decorator-5.1.0.tar.gz
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Other differences:
------------------
++++++ python-decorator.spec ++++++
--- /var/tmp/diff_new_pack.fKFNRr/_old 2021-10-20 20:24:17.621378423 +0200
+++ /var/tmp/diff_new_pack.fKFNRr/_new 2021-10-20 20:24:17.629378428 +0200
@@ -21,15 +21,13 @@
%{?!python_module:%define python_module() python-%{**} python3-%{**}}
%global skip_python2 1
Name: python-decorator
-Version: 5.0.9
+Version: 5.1.0
Release: 0
Summary: Decorators for Humans
License: BSD-2-Clause
Group: Development/Languages/Python
URL: https://github.com/micheles/decorator
Source:
https://files.pythonhosted.org/packages/source/d/decorator/decorator-%{version}.tar.gz
-# PATCH-FIX-UPSTREAM
https://github.com/micheles/decorator/commit/817d070db3c9cc5900d118837c533c039982b050
Fixed decorator.decorator not passing kwsyntax
-Patch0: kwsyntax.patch
BuildRequires: %{python_module setuptools}
BuildRequires: dos2unix
BuildRequires: fdupes
++++++ decorator-5.0.9.tar.gz -> decorator-5.1.0.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/decorator-5.0.9/CHANGES.md
new/decorator-5.1.0/CHANGES.md
--- old/decorator-5.0.9/CHANGES.md 2021-05-16 06:06:15.000000000 +0200
+++ new/decorator-5.1.0/CHANGES.md 2021-09-11 07:21:30.000000000 +0200
@@ -1,7 +1,15 @@
HISTORY
--------
-## unreleased
+## 5.1.0 (2021-09-11)
+
+Added a function `decoratorx` using the `FunctionMaker` and thus
+preserving the signature of `__code__` objects. Then fixed three small bugs:
+- Sphinx was printing a few warnings when building the documentation, as
+ signaled by Tomasz K??oczko
+- functions decorated with `decorator.contextmanager` were one-shot,
+ as discovered by Alex Pizarro.
+- `decorator.decorator` was not passing the kwsyntax argument.
## 5.0.9 (2021-05-16)
@@ -21,8 +29,8 @@
## 5.0.6 (2021-04-08)
-The decorator module was not copying the __module__ attribute anymore. Thanks
to
-Nikolay Markov for the notice.
+The decorator module was not copying the __module__ attribute anymore.
+Thanks to Nikolay Markov for the notice.
## 5.0.5 (2021-04-04)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/decorator-5.0.9/PKG-INFO new/decorator-5.1.0/PKG-INFO
--- old/decorator-5.0.9/PKG-INFO 2021-05-16 06:08:31.094942800 +0200
+++ new/decorator-5.1.0/PKG-INFO 2021-09-11 07:30:13.176995000 +0200
@@ -1,6 +1,6 @@
Metadata-Version: 1.2
Name: decorator
-Version: 5.0.9
+Version: 5.1.0
Summary: Decorators for Humans
Home-page: https://github.com/micheles/decorator
Author: Michele Simionato
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/decorator-5.0.9/src/decorator.egg-info/PKG-INFO
new/decorator-5.1.0/src/decorator.egg-info/PKG-INFO
--- old/decorator-5.0.9/src/decorator.egg-info/PKG-INFO 2021-05-16
06:08:30.000000000 +0200
+++ new/decorator-5.1.0/src/decorator.egg-info/PKG-INFO 2021-09-11
07:30:12.000000000 +0200
@@ -1,6 +1,6 @@
Metadata-Version: 1.2
Name: decorator
-Version: 5.0.9
+Version: 5.1.0
Summary: Decorators for Humans
Home-page: https://github.com/micheles/decorator
Author: Michele Simionato
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/decorator-5.0.9/src/decorator.py
new/decorator-5.1.0/src/decorator.py
--- old/decorator-5.0.9/src/decorator.py 2021-05-16 06:05:29.000000000
+0200
+++ new/decorator-5.1.0/src/decorator.py 2021-09-11 07:19:46.000000000
+0200
@@ -40,7 +40,7 @@
from contextlib import _GeneratorContextManager
from inspect import getfullargspec, iscoroutinefunction, isgeneratorfunction
-__version__ = '5.0.9'
+__version__ = '5.1.0'
DEF = re.compile(r'\s*def\s*([_\w][_\w\d]*)\s*\(')
POS = inspect.Parameter.POSITIONAL_OR_KEYWORD
@@ -259,13 +259,28 @@
return fun
+def decoratorx(caller):
+ """
+ A version of "decorator" implemented via "exec" and not via the
+ Signature object. Use this if you are want to preserve the `.__code__`
+ object properties (https://github.com/micheles/decorator/issues/129).
+ """
+ def dec(func):
+ return FunctionMaker.create(
+ func,
+ "return _call_(_func_, %(shortsignature)s)",
+ dict(_call_=caller, _func_=func),
+ __wrapped__=func, __qualname__=func.__qualname__)
+ return dec
+
+
def decorator(caller, _func=None, kwsyntax=False):
"""
decorator(caller) converts a caller function into a decorator
"""
if _func is not None: # return a decorated function
# this is obsolete behavior; you should use decorate instead
- return decorate(_func, caller)
+ return decorate(_func, caller, (), kwsyntax)
# else return a decorator function
sig = inspect.signature(caller)
dec_params = [p for p in sig.parameters.values() if p.kind is POS]
@@ -294,11 +309,11 @@
class ContextManager(_GeneratorContextManager):
def __init__(self, g, *a, **k):
- return _GeneratorContextManager.__init__(self, g, a, k)
+ _GeneratorContextManager.__init__(self, g, a, k)
def __call__(self, func):
def caller(f, *a, **k):
- with self:
+ with self._recreate_cm():
return f(*a, **k)
return decorate(func, caller)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/decorator-5.0.9/src/tests/documentation.py
new/decorator-5.1.0/src/tests/documentation.py
--- old/decorator-5.0.9/src/tests/documentation.py 2021-04-11
07:52:37.000000000 +0200
+++ new/decorator-5.1.0/src/tests/documentation.py 2021-09-11
07:28:23.000000000 +0200
@@ -1,4 +1,3 @@
-import sys
import inspect
import threading
import time
@@ -9,8 +8,7 @@
from decorator import (decorator, decorate, FunctionMaker,
dispatch_on, __version__)
-doc = r"""Decorators for Humans
-----------------------------------
+doc = r"""# Decorators for Humans
|Author | Michele Simionato|
|---|---|
@@ -21,8 +19,7 @@
|Installation| ``pip install decorator``|
|License | BSD license|
-Introduction
------------------------------------------
+## Introduction
The ``decorator`` module is over ten years old, but still alive and
kicking. It is used by several frameworks (IPython, scipy, authkit,
@@ -33,8 +30,7 @@
versions back to 2.6; versions 3.X are able to support even Python 2.5 and
2.4.
-What's New in version 5
------------------------
+## What's New in version 5
Version 5 of the decorator module features a major simplification of
the code base made possible by dropping support for Python releases
@@ -46,8 +42,7 @@
now possible to mimic the behavior of decorators defined with
``functool.wraps``: see the section about the ``kwsyntax`` flag below.
-What's New in version 4
------------------------
+## What's New in version 4
- **New documentation**
There is now a single manual for all Python versions, so I took the
@@ -86,8 +81,7 @@
From version 4.2 there is facility to define factories of decorators in
a simple way, a feature requested by the users since a long time.
-Usefulness of decorators
-------------------------------------------------
+## Usefulness of decorators
Python decorators are an interesting example of why syntactic sugar
matters. In principle, their introduction in Python 2.4 changed
@@ -117,8 +111,7 @@
discussed here in the ``documentation.py`` file, which contains
the documentation you are reading in the form of doctests.
-Definitions
-------------------------------------
+## Definitions
Technically speaking, any Python object which can be called with one argument
can be used as a decorator. However, this definition is somewhat too large
@@ -147,8 +140,7 @@
can accept functions with any signature. A simple example will clarify
the issue.
-Statement of the problem
-------------------------------
+## Statement of the problem
A very common use case for decorators is the memoization of functions.
A ``memoize`` decorator works by caching
@@ -212,8 +204,7 @@
Notice that ``pydoc`` will give the right signature, but only in Python
versions greater than 3.5.
-The solution
------------------------------------------
+## The solution
The solution is to provide a generic factory of generators, which
hides the complexity of making signature-preserving decorators
@@ -270,8 +261,7 @@
```
-A ``trace`` decorator
-------------------------------------------------------
+## A ``trace`` decorator
Here is an example of how to define a simple ``trace`` decorator,
which prints a message whenever the traced function is called:
@@ -320,10 +310,61 @@
```
-$FUNCTION_ANNOTATIONS
+## Function annotations
-``decorator.decorator``
----------------------------------------------
+Python 3 introduced the concept of [function annotations](
+http://www.python.org/dev/peps/pep-3107/): the ability
+to annotate the signature of a function with additional information,
+stored in a dictionary named ``__annotations__``. The ``decorator`` module
+(starting from release 3.3) will understand and preserve these annotations.
+
+Here is an example:
+
+```python
+>>> @trace
+... def f(x: 'the first argument', y: 'default argument'=1, z=2,
+... *args: 'varargs', **kw: 'kwargs'):
+... pass
+
+```
+
+In order to introspect functions with annotations, one needs
+``inspect.getfullargspec`` (introduced in Python 3, then
+deprecated in Python 3.5, then undeprecated in Python 3.6):
+
+```python
+>>> from inspect import getfullargspec
+>>> argspec = getfullargspec(f)
+>>> argspec.args
+['x', 'y', 'z']
+>>> argspec.varargs
+'args'
+>>> argspec.varkw
+'kw'
+>>> argspec.defaults
+(1, 2)
+>>> argspec.kwonlyargs
+[]
+>>> argspec.kwonlydefaults
+
+```
+
+You can check that the ``__annotations__`` dictionary is preserved:
+
+```python
+>>> f.__annotations__ is f.__wrapped__.__annotations__
+True
+
+```
+
+Here ``f.__wrapped__`` is the original undecorated function.
+This attribute exists for consistency with the behavior of
+``functools.update_wrapper``.
+
+Another attribute copied from the original function is ``__qualname__``,
+the qualified name. This attribute was introduced in Python 3.3.
+
+## ``decorator.decorator``
It can become tedious to write a caller function (like the above
``_trace`` example) and then a trivial wrapper
@@ -373,8 +414,7 @@
```
-Mimicking the behavior of functools.wrap
-----------------------------------------
+## Mimicking the behavior of functools.wrap
Often people are confused by the decorator module since, contrarily
to ``functools.wraps`` in the standard library, it tries very hard
@@ -433,8 +473,7 @@
```
-Decorator factories
--------------------------------------------
+## Decorator factories
The `decorator` function can also be used to define factories of decorators,
i.e. functions returning decorators. In general you can just write something
@@ -524,8 +563,7 @@
Be careful!
-``decorator(cls)``
---------------------------------------------
+## ``decorator(cls)``
The ``decorator`` facility can also produce a decorator starting
from a class with the signature of a caller. In such a case the
@@ -561,8 +599,7 @@
```
-contextmanager
--------------------------------------
+## contextmanager
Python's standard library has the ``contextmanager`` decorator,
which converts a generator function into a ``GeneratorContextManager``
@@ -599,11 +636,11 @@
```python
>>> ba = before_after('BEFORE', 'AFTER')
>>>
->>> @ba # doctest: +SKIP
+>>> @ba
... def hello():
... print('hello')
...
->>> hello() # doctest: +SKIP
+>>> hello()
BEFORE
hello
AFTER
@@ -627,8 +664,7 @@
an improved ``__call__`` method, which acts as a signature-preserving
decorator.
-The ``FunctionMaker`` class
----------------------------------------------------------------
+## The ``FunctionMaker`` class
The ``decorator`` module also provides a ``FunctionMaker`` class, which
is able to generate on-the-fly functions
@@ -718,8 +754,7 @@
```
-Getting the source code
----------------------------------------------------
+## Getting the source code
Internally, ``FunctionMaker.create`` uses ``exec`` to generate the
decorated function. Therefore ``inspect.getsource`` will not work for
@@ -742,8 +777,7 @@
```
-Dealing with third-party decorators
------------------------------------------------------------------
+## Dealing with third-party decorators
Sometimes on the net you find some cool decorator that you would
like to include in your code. However, more often than not, the cool
@@ -807,8 +841,7 @@
- returns a value without making a recursive call; or,
- returns directly the result of a recursive call.
-Python 3.5 coroutines
------------------------
+## Python 3.5 coroutines
I am personally not using Python 3.5 coroutines yet. However, some
users requested support for coroutines and since version 4.1 the
@@ -878,8 +911,7 @@
the caller in ``coro_to_func`` is a regular function and converts
coroutines -> functions.
-Multiple dispatch
--------------------------------------------
+## Multiple dispatch
There has been talk of implementing multiple dispatch functions
(i.e. "generic functions") in Python for over ten years. Last year,
@@ -1016,8 +1048,7 @@
[MRO](http://www.python.org/2.3/mro.html) for short) of ``StrongRock``
and ``Scissors``, respectively.
-Generic functions and virtual ancestors
--------------------------------------------------
+## Generic functions and virtual ancestors
In Python, generic functions are complicated by the existence of
"virtual ancestors": superclasses which are not in the class hierarchy.
@@ -1161,8 +1192,7 @@
Finally, let me notice that the decorator module implementation does
not use any cache, whereas the ``singledispatch`` implementation does.
-Caveats and limitations
--------------------------------------------
+## Caveats and limitations
In the present implementation, decorators generated by ``decorator``
can only be used on user-defined Python functions, methods or coroutines.
@@ -1172,6 +1202,40 @@
to look at the [wrapt](https://wrapt.readthedocs.io/en/latest/)
project by Graeme Dumpleton.
+Since version 5 the ``decorator`` module uses the ``inspect.Signature``
+object in the standard library. Unfortunately, for legacy reasons, some
+applications introspect decorated functions by using low-level entities like
+the ``__code__`` object and not signature objects. An example will make
+the issue clear:
+
+```python
+>>> def f(a, b): pass
+>>> f_dec = decorator(_trace)(f)
+>>> f_dec.__code__.co_argcount
+0
+>>> f_dec.__code__.co_varnames
+('args', 'kw')
+
+```
+This is not what one would expect: the `argcount` should be 2 since
+the original functions has two arguments and the `varnames` should be
+`a` and `b`. The only way to fix the issue is to go back to an implementation
+of the decorator using ``exec``, which is provided for convenience since
+version 5.1:
+
+```python
+>>> from decorator import decoratorx
+>>> f_dec = decoratorx(_trace)(f)
+>>> f_dec.__code__.co_argcount
+2
+>>> f_dec.__code__.co_varnames
+('a', 'b')
+
+```
+Rather than using `decoratorx`, you should fix your introspection
+routines to use ``inspect.Signature`` without fiddling with the
+``__code__`` object.
+
There is a strange quirk when decorating functions with keyword
arguments, if one of the arguments has the same name used in the
caller function for the first argument. The quirk was reported by
@@ -1276,8 +1340,7 @@
*could* be negligible. As always, the only way to know if there is a
penalty in your specific use case is to measure it.
-LICENSE (2-clause BSD)
----------------------------------------------
+## LICENSE (2-clause BSD)
Copyright (c) 2005-2020, Michele Simionato
All rights reserved.
@@ -1311,68 +1374,9 @@
you are unhappy with it, send me a patch!
"""
-function_annotations = """Function annotations
----------------------------------------------
-
-Python 3 introduced the concept of [function annotations](
-http://www.python.org/dev/peps/pep-3107/): the ability
-to annotate the signature of a function with additional information,
-stored in a dictionary named ``__annotations__``. The ``decorator`` module
-(starting from release 3.3) will understand and preserve these annotations.
-
-Here is an example:
-
-```python
->>> @trace
-... def f(x: 'the first argument', y: 'default argument'=1, z=2,
-... *args: 'varargs', **kw: 'kwargs'):
-... pass
-
-```
-
-In order to introspect functions with annotations, one needs
-``inspect.getfullargspec`` (introduced in Python 3, then
-deprecated in Python 3.5, then undeprecated in Python 3.6):
-
-```python
->>> from inspect import getfullargspec
->>> argspec = getfullargspec(f)
->>> argspec.args
-['x', 'y', 'z']
->>> argspec.varargs
-'args'
->>> argspec.varkw
-'kw'
->>> argspec.defaults
-(1, 2)
->>> argspec.kwonlyargs
-[]
->>> argspec.kwonlydefaults
-
-```
-
-You can check that the ``__annotations__`` dictionary is preserved:
-
-```python
->>> f.__annotations__ is f.__wrapped__.__annotations__
-True
-
-```
-
-Here ``f.__wrapped__`` is the original undecorated function.
-This attribute exists for consistency with the behavior of
-``functools.update_wrapper``.
-
-Another attribute copied from the original function is ``__qualname__``,
-the qualified name. This attribute was introduced in Python 3.3.
-"""
-if sys.version_info < (3,):
- function_annotations = ''
-
today = time.strftime('%Y-%m-%d')
-__doc__ = (doc.replace('$VERSION', __version__).replace('$DATE', today)
- .replace('$FUNCTION_ANNOTATIONS', function_annotations))
+__doc__ = doc.replace('$VERSION', __version__).replace('$DATE', today)
def decorator_apply(dec, func):