Script 'mail_helper' called by obssrc
Hello community,

here is the log from the commit of package python-aioitertools for 
openSUSE:Factory checked in at 2021-08-28 22:29:23
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-aioitertools (Old)
 and      /work/SRC/openSUSE:Factory/.python-aioitertools.new.1899 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "python-aioitertools"

Sat Aug 28 22:29:23 2021 rev:3 rq:914749 version:0.8.0

Changes:
--------
--- /work/SRC/openSUSE:Factory/python-aioitertools/python-aioitertools.changes  
2021-05-13 22:18:59.163495261 +0200
+++ 
/work/SRC/openSUSE:Factory/.python-aioitertools.new.1899/python-aioitertools.changes
        2021-08-28 22:29:49.402018971 +0200
@@ -1,0 +2,13 @@
+Tue Aug 17 10:11:54 UTC 2021 - John Paul Adrian Glaubitz 
<[email protected]>
+
+- Update to 0.8.0:
+  - Added `builtins.any()` and `builtins.all()` (#44)
+  - `builtins.next()` takes an optional `default` parameter (#40, #41)
+  - `asyncio.gather()` now handles cancellation (#64)
+  - Better exception handling in `itertools.tee()` (#47)
+  - Removed dependency on typing_extensions for Python 3.8 and newer (#49)
+  - Improved documentation and formatting
+- Drop patches for issues fixed upstream
+  - stdlib-typing_extensions.patch
+
+-------------------------------------------------------------------

Old:
----
  aioitertools-0.7.1.tar.gz
  stdlib-typing_extensions.patch

New:
----
  aioitertools-0.8.0.tar.gz

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ python-aioitertools.spec ++++++
--- /var/tmp/diff_new_pack.Gs9G80/_old  2021-08-28 22:29:49.902019527 +0200
+++ /var/tmp/diff_new_pack.Gs9G80/_new  2021-08-28 22:29:49.906019531 +0200
@@ -19,16 +19,13 @@
 %{?!python_module:%define python_module() python-%{**} python3-%{**}}
 %define skip_python2 1
 Name:           python-aioitertools
-Version:        0.7.1
+Version:        0.8.0
 Release:        0
 Summary:        itertools and builtins for AsyncIO and mixed iterables
 License:        MIT
 Group:          Development/Languages/Python
 URL:            https://aioitertools.omnilib.dev
 Source:         
https://files.pythonhosted.org/packages/source/a/aioitertools/aioitertools-%{version}.tar.gz
-# PATCH-FIX-UPSTREAM stdlib-typing_extensions.patch gh#omnilib/aioitertools#49 
[email protected]
-# Improve dependencies for Python 3.8+
-Patch0:         stdlib-typing_extensions.patch
 BuildRequires:  %{python_module asyncio}
 BuildRequires:  %{python_module setuptools}
 BuildRequires:  %{python_module typing_extensions if %python-base < 3.8}

++++++ aioitertools-0.7.1.tar.gz -> aioitertools-0.8.0.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/.flake8 
new/aioitertools-0.8.0/.flake8
--- old/aioitertools-0.7.1/.flake8      1970-01-01 01:00:00.000000000 +0100
+++ new/aioitertools-0.8.0/.flake8      2021-05-16 22:57:53.159477500 +0200
@@ -0,0 +1,13 @@
+[flake8]
+ignore =
+    # mccabe complexity
+    C901
+
+    # covered by black/usort
+    E1
+    E2
+    E3
+    E4
+max-line-length = 88
+per-file-ignores =
+    __init__.py: F401
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/CHANGELOG.md 
new/aioitertools-0.8.0/CHANGELOG.md
--- old/aioitertools-0.7.1/CHANGELOG.md 2020-11-09 04:56:44.066201000 +0100
+++ new/aioitertools-0.8.0/CHANGELOG.md 2021-08-05 04:24:00.792124300 +0200
@@ -1,6 +1,31 @@
 aioitertools
 ============
 
+v0.8.0
+------
+
+Feature release:
+
+- Added `builtins.any()` and `builtins.all()` (#44)
+- `builtins.next()` takes an optional `default` parameter (#40, #41)
+- `asyncio.gather()` now handles cancellation (#64)
+- Better exception handling in `itertools.tee()` (#47)
+- Removed dependency on typing_extensions for Python 3.8 and newer (#49)
+- Improved documentation and formatting
+
+```
+$ git shortlog -s v0.7.1...v0.8.0
+     1 Bryan Forbes
+     2 Jason Fried
+    15 John Reese
+     1 Kevin Stone
+     3 Roger Aiudi
+     3 Sunyeop Lee
+     1 Yop
+    10 pyup.io bot
+```
+
+
 v0.7.1
 ------
 
@@ -176,7 +201,7 @@
 - Unit tests for all builtins
 
 ```
-$ git shortlog -s ce32bdb1777f84e8f64b9470d81b84b754389dd9...v0.1.0
-     1 John Reese
+$ git shortlog -s v0.1.0
+     2 John Reese
 ```
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/PKG-INFO 
new/aioitertools-0.8.0/PKG-INFO
--- old/aioitertools-0.7.1/PKG-INFO     1970-01-01 01:00:00.000000000 +0100
+++ new/aioitertools-0.8.0/PKG-INFO     1970-01-01 01:00:00.000000000 +0100
@@ -1,7 +1,109 @@
-Metadata-Version: 1.1
+Metadata-Version: 2.1
 Name: aioitertools
-Version: 0.7.1
+Version: 0.8.0
 Summary: itertools and builtins for AsyncIO and mixed iterables
 Home-page: https://aioitertools.omnilib.dev
 Author: John Reese
 Author-email: [email protected]
+Requires-Python: >=3.6
+Description-Content-Type: text/markdown
+Classifier: Development Status :: 4 - Beta
+Classifier: Framework :: AsyncIO
+Classifier: Intended Audience :: Developers
+Classifier: License :: OSI Approved :: MIT License
+Classifier: Topic :: Software Development :: Libraries
+Requires-Dist: typing_extensions>=3.7; python_version < '3.8'
+Project-URL: Documentation, https://aioitertools.omnilib.dev/en/latest/
+Project-URL: Github, https://github.com/omnilib/aioitertools
+
+aioitertools
+============
+
+Implementation of itertools, builtins, and more for AsyncIO and mixed-type 
iterables.
+
+[![build 
status](https://github.com/omnilib/aioitertools/workflows/Build/badge.svg)](https://github.com/omnilib/aioitertools/actions)
+[![code 
coverage](https://img.shields.io/codecov/c/gh/omnilib/aioitertools)](https://codecov.io/gh/omnilib/aioitertools)
+[![version](https://img.shields.io/pypi/v/aioitertools.svg)](https://pypi.org/project/aioitertools)
+[![license](https://img.shields.io/pypi/l/aioitertools.svg)](https://github.com/omnilib/aioitertools/blob/master/LICENSE)
+[![code 
style](https://img.shields.io/badge/code%20style-black-000000.svg)](https://github.com/ambv/black)
+
+
+Install
+-------
+
+aioitertools requires Python 3.6 or newer.
+You can install it from PyPI:
+
+    $ pip install aioitertools
+
+
+Usage
+-----
+
+aioitertools shadows the standard library whenever possible to provide
+asynchronous version of the modules and functions you already know.  It's
+fully compatible with standard iterators and async iterators alike, giving
+you one unified,??familiar interface for interacting with iterable objects:
+
+```python
+from aioitertools import iter, next, map, zip
+
+something = iter(...)
+first_item = await next(something)
+
+async for item in iter(something):
+    ...
+
+
+async def fetch(url):
+    response = await aiohttp.request(...)
+    return response.json
+
+async for value in map(fetch, MANY_URLS):
+    ...
+
+
+async for a, b in zip(something, something_else):
+    ...
+```
+
+
+aioitertools emulates the entire `itertools` module, offering the same
+function signatures, but as async generators.  All functions support
+standard iterables and async iterables alike, and can take functions or
+coroutines:
+
+```python
+from aioitertools import chain, islice
+
+async def generator1(...):
+    yield ...
+
+async def generator2(...):
+    yield ...
+
+async for value in chain(generator1(), generator2()):
+    ...
+
+async for value in islice(generator1(), 2, None, 2):
+    ...
+```
+
+
+See [builtins.py][], [itertools.py][], and [more_itertools.py][] for full
+documentation of functions and abilities.
+
+
+License
+-------
+
+aioitertools is copyright [John Reese](https://jreese.sh), and licensed under
+the MIT license.  I am providing code in this repository to you under an open
+source license.  This is my personal repository; the license you receive to
+my code is from me and not from my employer. See the `LICENSE` file for 
details.
+
+
+[builtins.py]: 
https://github.com/omnilib/aioitertools/blob/master/aioitertools/builtins.py
+[itertools.py]: 
https://github.com/omnilib/aioitertools/blob/master/aioitertools/itertools.py
+[more_itertools.py]: 
https://github.com/omnilib/aioitertools/blob/master/aioitertools/more_itertools.py
+
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/__init__.py 
new/aioitertools-0.8.0/aioitertools/__init__.py
--- old/aioitertools-0.7.1/aioitertools/__init__.py     2020-11-09 
04:47:28.899267000 +0100
+++ new/aioitertools-0.8.0/aioitertools/__init__.py     2021-08-05 
04:22:56.171010700 +0200
@@ -8,7 +8,20 @@
 __author__ = "John Reese"
 from . import asyncio
 from .__version__ import __version__
-from .builtins import enumerate, iter, list, map, max, min, next, set, sum, zip
+from .builtins import (
+    all,
+    any,
+    enumerate,
+    iter,
+    list,
+    map,
+    max,
+    min,
+    next,
+    set,
+    sum,
+    zip,
+)
 from .itertools import (
     accumulate,
     chain,
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/__version__.py 
new/aioitertools-0.8.0/aioitertools/__version__.py
--- old/aioitertools-0.7.1/aioitertools/__version__.py  2020-11-09 
04:56:44.081393200 +0100
+++ new/aioitertools-0.8.0/aioitertools/__version__.py  2021-08-05 
04:24:00.800830100 +0200
@@ -1 +1 @@
-__version__ = "0.7.1"
+__version__ = "0.8.0"
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/asyncio.py 
new/aioitertools-0.8.0/aioitertools/asyncio.py
--- old/aioitertools-0.7.1/aioitertools/asyncio.py      2020-11-09 
04:47:28.889947000 +0100
+++ new/aioitertools-0.8.0/aioitertools/asyncio.py      2021-08-05 
04:22:56.166504100 +0200
@@ -11,7 +11,8 @@
 import time
 from typing import Any, Awaitable, Dict, Iterable, List, Optional, Set, Tuple, 
cast
 
-from .types import AsyncIterator, T
+from .builtins import maybe_await, iter as aiter
+from .types import AsyncIterator, MaybeAwaitable, AnyIterable, T
 
 
 async def as_completed(
@@ -26,7 +27,7 @@
     Unlike `asyncio.as_completed`, this yields actual results, and does not 
require
     awaiting each item in the iterable.
 
-    Example:
+    Example::
 
         async for value in as_completed(futures):
             ...  # use value immediately
@@ -52,8 +53,8 @@
         # returns Tuple[Set[Future], Set[Future]. Because mypy doesn't like 
assigning
         # these values to existing Set[Awaitable] or even Set[Union[Awaitable, 
Future]],
         # we need to first cast the results to something that we can actually 
use
-        # asyncio.Future: 
https://github.com/python/typeshed/blob/72ff7b94e534c610ddf8939bacbc55343e9465d2/stdlib/3/asyncio/futures.pyi#L30
-        # asyncio.wait(): 
https://github.com/python/typeshed/blob/72ff7b94e534c610ddf8939bacbc55343e9465d2/stdlib/3/asyncio/tasks.pyi#L89
+        # asyncio.Future: 
https://github.com/python/typeshed/blob/72ff7b94e534c610ddf8939bacbc55343e9465d2/stdlib/3/asyncio/futures.pyi#L30
  # noqa: E501
+        # asyncio.wait(): 
https://github.com/python/typeshed/blob/72ff7b94e534c610ddf8939bacbc55343e9465d2/stdlib/3/asyncio/tasks.pyi#L89
  # noqa: E501
         done, pending = cast(
             Tuple[Set[Awaitable[T]], Set[Awaitable[T]]],
             await asyncio.wait(
@@ -74,10 +75,19 @@
     return_exceptions: bool = False,
     limit: int = -1
 ) -> List[Any]:
-    """Like asyncio.gather but with a limit on concurrency.
+    """
+    Like asyncio.gather but with a limit on concurrency.
+
+    Note that all results are buffered.
+
+    If gather is cancelled all tasks that were internally created and still 
pending
+    will be cancelled as well.
 
-    Much of the complexity of gather comes with it support for cancel, which we
-    omit here.  Note that all results are buffered.
+    Example::
+
+        futures = [some_coro(i) for i in range(10)]
+
+        results = await gather(*futures, limit=2)
     """
 
     # For detecting input duplicates and reconciling them at the end
@@ -112,14 +122,22 @@
         # pending might be empty if the last items of args were dupes;
         # asyncio.wait([]) will raise an exception.
         if pending:
-            done, pending = await asyncio.wait(
-                pending, loop=loop, return_when=asyncio.FIRST_COMPLETED
-            )
-            for x in done:
-                if return_exceptions and x.exception():
-                    ret[pos[x]] = x.exception()
-                else:
-                    ret[pos[x]] = x.result()
+            try:
+                done, pending = await asyncio.wait(
+                    pending, loop=loop, return_when=asyncio.FIRST_COMPLETED
+                )
+                for x in done:
+                    if return_exceptions and x.exception():
+                        ret[pos[x]] = x.exception()
+                    else:
+                        ret[pos[x]] = x.result()
+            except asyncio.CancelledError:
+                # Since we created these tasks we should cancel them
+                for x in pending:
+                    x.cancel()
+                # we insure that all tasks are cancelled before we raise
+                await asyncio.gather(*pending, loop=loop, 
return_exceptions=True)
+                raise
 
         if not pending and next_arg == len(args):
             break
@@ -129,3 +147,22 @@
             ret[lst[i]] = ret[lst[0]]
 
     return ret
+
+
+async def gather_iter(
+    itr: AnyIterable[MaybeAwaitable[T]],
+    loop: Optional[asyncio.AbstractEventLoop] = None,
+    return_exceptions: bool = False,
+    limit: int = -1,
+) -> List[T]:
+    """
+    Wrapper around gather to handle gathering an iterable instead of *args.
+
+    Note that the iterable values don't have to be awaitable.
+    """
+    return await gather(
+        *[maybe_await(i) async for i in aiter(itr)],
+        loop=loop,
+        return_exceptions=return_exceptions,
+        limit=limit,
+    )
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/builtins.py 
new/aioitertools-0.8.0/aioitertools/builtins.py
--- old/aioitertools-0.7.1/aioitertools/builtins.py     2020-11-09 
04:47:28.821214700 +0100
+++ new/aioitertools-0.8.0/aioitertools/builtins.py     2021-08-05 
04:22:57.200909100 +0200
@@ -13,6 +13,7 @@
 
 import asyncio
 import builtins
+from enum import Enum
 from typing import (
     Any,
     AsyncIterable,
@@ -28,8 +29,59 @@
     overload,
 )
 
+from . import asyncio as ait_asyncio
 from .helpers import Orderable, maybe_await
-from .types import T1, T2, T3, T4, T5, AnyIterable, AnyIterator, AnyStop, R, T
+from .types import (
+    T1,
+    T2,
+    T3,
+    T4,
+    T5,
+    AnyIterable,
+    AnyIterator,
+    AnyStop,
+    R,
+    T,
+    MaybeAwaitable,
+)
+
+
+class Sentinel(Enum):
+    """
+    :meta private:
+    """
+
+    MISSING = object()
+
+
+async def all(itr: AnyIterable[MaybeAwaitable[Any]]) -> bool:
+    """
+    Return True if all values are truthy in a mixed iterable, else False.
+    The iterable will be fully consumed and any awaitables will
+    automatically be awaited.
+
+    Example::
+
+        if await all(it):
+            ...
+
+    """
+    return builtins.all(await ait_asyncio.gather_iter(itr))
+
+
+async def any(itr: AnyIterable[MaybeAwaitable[Any]]) -> bool:
+    """
+    Return True if any value is truthy in a mixed iterable, else False.
+    The iterable will be fully consumed and any awaitables will
+    automatically be awaited.
+
+    Example::
+
+        if await any(it):
+            ...
+
+    """
+    return builtins.any(await ait_asyncio.gather_iter(itr))
 
 
 def iter(itr: AnyIterable[T]) -> AsyncIterator[T]:
@@ -41,9 +93,9 @@
     Standard iterables will be wrapped in an async generator yielding
     each item in the iterable in the same order.
 
-    Examples:
+    Examples::
 
-        async for iter(range(10)):
+        async for value in iter(range(10)):
             ...
 
     """
@@ -60,32 +112,49 @@
     return gen()
 
 
+@overload
 async def next(itr: AnyIterator[T]) -> T:
+    ...
+
+
+@overload
+async def next(itr: AnyIterator[T1], default: T2) -> Union[T1, T2]:
+    ...
+
+
+async def next(
+    itr: AnyIterator[T1], default: Union[T2, Sentinel] = Sentinel.MISSING
+) -> Union[T1, T2]:
     """
     Return the next item of any mixed iterator.
 
     Calls builtins.next() on standard iterators, and awaits itr.__anext__()
     on async iterators.
 
-    Example:
+    Example::
 
         value = await next(it)
 
     """
-    if isinstance(itr, AsyncIterator):
-        return await itr.__anext__()
-
     try:
-        return builtins.next(itr)
-    except StopIteration:
-        raise StopAsyncIteration
+        if isinstance(itr, AsyncIterator):
+            return await itr.__anext__()
+
+        try:
+            return builtins.next(itr)
+        except StopIteration:
+            raise StopAsyncIteration
+    except StopAsyncIteration:
+        if default is Sentinel.MISSING:
+            raise
+        return default
 
 
 async def list(itr: AnyIterable[T]) -> List[T]:
     """
     Consume a mixed iterable and return a list of items in order.
 
-    Example:
+    Example::
 
         await list(range(5))
         -> [0, 1, 2, 3, 4]
@@ -98,7 +167,7 @@
     """
     Consume a mixed iterable and return a set of items.
 
-    Example:
+    Example::
 
         await set([0, 1, 2, 3, 0, 1, 2, 3])
         -> {0, 1, 2, 3}
@@ -113,7 +182,7 @@
     """
     Consume a mixed iterable and yield the current index and item.
 
-    Example:
+    Example::
 
         async for index, value in enumerate(...):
             ...
@@ -129,7 +198,7 @@
     """
     Modify item of a mixed iterable using the given function or coroutine.
 
-    Example:
+    Example::
 
         async for response in map(func, data):
             ...
@@ -158,7 +227,7 @@
     """
     Return the largest item in an iterable or the largest of two or more 
arguments.
 
-    Example:
+    Example::
 
         await min(range(5))
         -> 4
@@ -217,7 +286,7 @@
     """
     Return the smallest item in an iterable or the smallest of two or more 
arguments.
 
-    Example:
+    Example::
 
         await min(range(5))
         -> 0
@@ -262,7 +331,7 @@
     """
     Compute the sum of a mixed iterable, adding each value with the start 
value.
 
-    Example:
+    Example::
 
         await sum(generator())
         -> 1024
@@ -280,7 +349,6 @@
     return value
 
 
-# pylint: disable=undefined-variable,multiple-statements,too-many-arguments
 @overload
 def zip(__iter1: AnyIterable[T1]) -> AsyncIterator[Tuple[T1]]:  # pragma: no 
cover
     pass
@@ -334,12 +402,11 @@
     pass
 
 
-# pylint: enable=undefined-variable,multiple-statements,too-many-arguments
 async def zip(*itrs: AnyIterable[Any]) -> AsyncIterator[Tuple[Any, ...]]:
     """
     Yield a tuple of items from mixed iterables until the shortest is consumed.
 
-    Example:
+    Example::
 
         async for a, b, c in zip(i, j, k):
             ...
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/helpers.py 
new/aioitertools-0.8.0/aioitertools/helpers.py
--- old/aioitertools-0.7.1/aioitertools/helpers.py      2020-11-09 
04:47:28.965547800 +0100
+++ new/aioitertools-0.8.0/aioitertools/helpers.py      2021-08-05 
04:22:56.191383400 +0200
@@ -2,12 +2,16 @@
 # Licensed under the MIT license
 
 import inspect
+import sys
 from typing import Awaitable, Union
 
-from typing_extensions import Protocol
-
 from .types import T
 
+if sys.version_info < (3, 8):
+    from typing_extensions import Protocol
+else:
+    from typing import Protocol
+
 
 class Orderable(Protocol):  # pragma: no cover
     def __lt__(self, other):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/itertools.py 
new/aioitertools-0.8.0/aioitertools/itertools.py
--- old/aioitertools-0.7.1/aioitertools/itertools.py    2020-11-09 
04:47:29.179919700 +0100
+++ new/aioitertools-0.8.0/aioitertools/itertools.py    2021-08-05 
04:22:56.255954300 +0200
@@ -43,7 +43,7 @@
 
     Accepts both a standard function or a coroutine for accumulation.
 
-    Example:
+    Example::
 
         data = [1, 2, 3, 4]
 
@@ -73,7 +73,7 @@
 
         Consumes the first iterable lazily, in entirety, then the second, and 
so on.
 
-        Example:
+        Example::
 
             async for value in chain([1, 2, 3], [7, 8, 9]):
                 ...  # 1, 2, 3, 7, 8, 9
@@ -102,7 +102,7 @@
     Simple wrapper around itertools.combinations for asyncio.
     This will consume the entire iterable before yielding values.
 
-    Example:
+    Example::
 
         async for value in combinations(range(4), 3):
             ...  # (0, 1, 2), (0, 1, 3), (0, 2, 3), (1, 2, 3)
@@ -122,7 +122,7 @@
     Simple wrapper around itertools.combinations_with_replacement.
     This will consume the entire iterable before yielding values.
 
-    Example:
+    Example::
 
         async for value in combinations_with_replacement("ABC", 2):
             ...  # ("A", "A"), ("A", "B"), ("A", "C"), ("B", "B"), ...
@@ -141,7 +141,7 @@
 
     Stops when either the iterable or the selectors have been exhausted.
 
-    Example:
+    Example::
 
         async for value in compress(range(5), [1, 0, 0, 1, 1]):
             ...  # 0, 3, 4
@@ -155,7 +155,7 @@
     """
     Yield an infinite series, starting at the given value and increasing by 
step.
 
-    Example:
+    Example::
 
         async for value in counter(10, -1):
             ...  # 10, 9, 8, 7, ...
@@ -175,7 +175,7 @@
     Lazily consumes the iterable when the next value is needed, and caching
     the values in memory for future iterations of the series.
 
-    Example:
+    Example::
 
         async for value in cycle([1, 2]):
             ...  # 1, 2, 1, 2, 1, 2, ...
@@ -199,7 +199,7 @@
 
     Accepts both standard functions and coroutines for the predicate.
 
-    Example:
+    Example::
 
         def pred(x):
             return x < 4
@@ -225,7 +225,7 @@
 
     Accepts both standard functions and coroutines for the predicate.
 
-    Example:
+    Example::
 
         def pred(x):
             return x < 4
@@ -239,7 +239,6 @@
             yield item
 
 
-# pylint: disable=undefined-variable,multiple-statements
 @overload
 def groupby(itr: AnyIterable[T]) -> AsyncIterator[Tuple[T, List[T]]]:  # 
pragma: nocover
     pass
@@ -252,7 +251,6 @@
     pass
 
 
-# pylint: enable=undefined-variable,multiple-statements
 async def groupby(
     itr: AnyIterable[T], key: Optional[KeyFunction[T, R]] = None
 ) -> AsyncIterator[Tuple[Any, List[T]]]:
@@ -264,7 +262,7 @@
     coroutines for the key function.  Suggest sorting by the key
     function before using groupby.
 
-    Example:
+    Example::
 
         data = ["A", "a", "b", "c", "C", "c"]
 
@@ -274,7 +272,7 @@
 
     """
     if key is None:
-        key = lambda x: x
+        key = lambda x: x  # noqa: E731
 
     grouping: List[T] = []
 
@@ -298,7 +296,6 @@
     yield j, grouping
 
 
-# pylint: disable=undefined-variable,multiple-statements
 @overload
 def islice(
     itr: AnyIterable[T], __stop: Optional[int]
@@ -313,7 +310,6 @@
     pass
 
 
-# pylint: enable=undefined-variable,multiple-statements
 async def islice(itr: AnyIterable[T], *args: Optional[int]) -> 
AsyncIterator[T]:
     """
     Yield selected items from the given iterable.
@@ -324,7 +320,7 @@
     Starting from the start index (or zero), stopping at the stop
     index (or until exhausted), skipping items if step > 0.
 
-    Example:
+    Example::
 
         data = range(10)
 
@@ -372,7 +368,7 @@
     Simple wrapper around itertools.combinations for asyncio.
     This will consume the entire iterable before yielding values.
 
-    Example:
+    Example::
 
         async for value in permutations(range(3)):
             ...  # (0, 1, 2), (0, 2, 1), (1, 0, 2), ...
@@ -384,7 +380,7 @@
 
 
 async def product(
-    *itrs: AnyIterable[T], repeat: int = 1  # pylint: 
disable=redefined-outer-name
+    *itrs: AnyIterable[T], repeat: int = 1
 ) -> AsyncIterator[Tuple[T, ...]]:
     """
     Yield cartesian products of all iterables.
@@ -392,7 +388,7 @@
     Simple wrapper around itertools.combinations for asyncio.
     This will consume all iterables before yielding any values.
 
-    Example:
+    Example::
 
         async for value in product("abc", "xy"):
             ...  # ("a", "x"), ("a", "y"), ("b", "x"), ...
@@ -410,7 +406,7 @@
     """
     Yield the given value repeatedly, forever or up to n times.
 
-    Example:
+    Example::
 
         async for value in repeat(7):
             ...  # 7, 7, 7, 7, 7, 7, ...
@@ -432,7 +428,7 @@
     Each iterable contained within will be unpacked and consumed before
     executing the function or coroutine.
 
-    Example:
+    Example::
 
         data = [(1, 1), (1, 1, 1), (2, 2)]
 
@@ -453,7 +449,7 @@
 
     Accepts both standard functions and coroutines for the predicate.
 
-    Example:
+    Example::
 
         def pred(x):
             return x < 4
@@ -483,7 +479,7 @@
     used in keeping values in the queues until the other iterators finish
     consuming them.
 
-    Example:
+    Example::
 
         it1, it2 = tee(range(5), n=2)
 
@@ -500,15 +496,23 @@
 
     async def gen(k: int, q: asyncio.Queue) -> AsyncIterator[T]:
         if k == 0:
-            async for value in iter(itr):
-                await asyncio.gather(*[queue.put(value) for queue in 
queues[1:]])
-                yield value
+            try:
+                async for value in iter(itr):
+                    await asyncio.gather(
+                        *[queue.put((None, value)) for queue in queues[1:]]
+                    )
+                    yield value
+            except Exception as e:
+                await asyncio.gather(*[queue.put((e, None)) for queue in 
queues[1:]])
+                raise
 
-            await asyncio.gather(*[queue.put(sentinel) for queue in 
queues[1:]])
+            await asyncio.gather(*[queue.put((None, sentinel)) for queue in 
queues[1:]])
 
         else:
             while True:
-                value = await q.get()
+                error, value = await q.get()
+                if error is not None:
+                    raise error
                 if value is sentinel:
                     break
                 yield value
@@ -525,7 +529,7 @@
     If shorter iterables are exhausted, the default value will be used
     until all iterables are exhausted.
 
-    Example:
+    Example::
 
         a = range(3)
         b = range(5)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/more_itertools.py 
new/aioitertools-0.8.0/aioitertools/more_itertools.py
--- old/aioitertools-0.7.1/aioitertools/more_itertools.py       2020-11-09 
04:47:28.950679500 +0100
+++ new/aioitertools-0.8.0/aioitertools/more_itertools.py       2021-08-05 
04:22:56.186720100 +0200
@@ -17,7 +17,7 @@
     If there are too few items in iterable, all of them are returned.
     n needs to be at least 0. If it is 0, an empty list is returned.
 
-    Example:
+    Example::
 
         first_two = await take(2, [1, 2, 3, 4, 5])
 
@@ -34,7 +34,7 @@
     The last chunk will be shorter if the total number of items is not
     divisible by n.
 
-    Example:
+    Example::
 
         async for chunk in chunked([1, 2, 3, 4, 5], n=2):
             ...  # first iteration: chunk == [1, 2]; last one: chunk == [5]
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/tests/asyncio.py 
new/aioitertools-0.8.0/aioitertools/tests/asyncio.py
--- old/aioitertools-0.7.1/aioitertools/tests/asyncio.py        2020-11-09 
04:47:29.478941200 +0100
+++ new/aioitertools-0.8.0/aioitertools/tests/asyncio.py        2021-08-05 
04:22:56.366293200 +0200
@@ -59,7 +59,7 @@
         fns = [fn(1), asyncio.ensure_future(fn(2))]
         if hasattr(asyncio, "create_task"):
             # 3.7 only
-            fns.append(asyncio.create_task(fn(3)))  # pylint: disable=no-member
+            fns.append(asyncio.create_task(fn(3)))
         else:
             fns.append(fn(3))
 
@@ -74,8 +74,7 @@
         async def fn(arg):
             nonlocal counter, max_counter
             counter += 1
-            if max_counter < counter:
-                max_counter = counter
+            max_counter = max(max_counter, counter)
             await asyncio.sleep(0.001)
             counter -= 1
             return arg
@@ -127,3 +126,34 @@
         )
         self.assertEqual(result[1], 0.001)
         self.assertIsInstance(result[0], MyException)
+
+    @async_test
+    async def test_gather_cancel(self):
+        cancelled = False
+        started = False
+
+        async def _fn():
+            nonlocal started, cancelled
+            try:
+                started = True
+                await asyncio.sleep(10)  # might as well be forever
+            except asyncio.CancelledError:
+                nonlocal cancelled
+                cancelled = True
+                raise
+
+        async def _gather():
+            await aio.gather(_fn())
+
+        if hasattr(asyncio, "create_task"):
+            # 3.7+ only
+            task = asyncio.create_task(_gather())
+        else:
+            task = asyncio.ensure_future(_gather())
+        # to insure the gather actually runs
+        await asyncio.sleep(0)
+        task.cancel()
+        with self.assertRaises(asyncio.CancelledError):
+            await task
+        self.assertTrue(started)
+        self.assertTrue(cancelled)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/tests/builtins.py 
new/aioitertools-0.8.0/aioitertools/tests/builtins.py
--- old/aioitertools-0.7.1/aioitertools/tests/builtins.py       2020-11-09 
04:47:29.375778400 +0100
+++ new/aioitertools-0.8.0/aioitertools/tests/builtins.py       2021-08-05 
04:22:56.331863200 +0200
@@ -10,10 +10,59 @@
 
 slist = ["A", "B", "C"]
 srange = range(3)
+srange1 = range(1, 4)
+srange0 = range(1)
 
 
 class BuiltinsTest(TestCase):
 
+    # aioitertools.all()
+
+    @async_test
+    async def test_all_list(self):
+        self.assertTrue(await ait.all([True, 1, "string"]))
+        self.assertFalse(await ait.all([True, 0, "string"]))
+
+    @async_test
+    async def test_all_range(self):
+        self.assertTrue(await ait.all(srange1))
+        self.assertFalse(await ait.all(srange))
+
+    @async_test
+    async def test_all_generator(self):
+        self.assertTrue(await ait.all(x for x in srange1))
+        self.assertFalse(await ait.all(x for x in srange))
+
+    @async_test
+    async def test_all_async_generator(self):
+        self.assertTrue(await ait.all(ait.iter(srange1)))
+        self.assertFalse(await ait.all(ait.iter(srange)))
+
+    # aioitertools.any()
+
+    @async_test
+    async def test_any_list(self):
+        self.assertTrue(await ait.any([False, 1, ""]))
+        self.assertFalse(await ait.any([False, 0, ""]))
+
+    @async_test
+    async def test_any_range(self):
+        self.assertTrue(await ait.any(srange))
+        self.assertTrue(await ait.any(srange1))
+        self.assertFalse(await ait.any(srange0))
+
+    @async_test
+    async def test_any_generator(self):
+        self.assertTrue(await ait.any(x for x in srange))
+        self.assertTrue(await ait.any(x for x in srange1))
+        self.assertFalse(await ait.any(x for x in srange0))
+
+    @async_test
+    async def test_any_async_generator(self):
+        self.assertTrue(await ait.any(ait.iter(srange)))
+        self.assertTrue(await ait.any(ait.iter(srange1)))
+        self.assertFalse(await ait.any(ait.iter(srange0)))
+
     # aioitertools.iter()
 
     @async_test
@@ -134,6 +183,21 @@
         with self.assertRaises(StopAsyncIteration):
             await ait.next(it)
 
+    @async_test
+    async def test_next_default_iterable(self):
+        it = iter(["A"])
+
+        self.assertEqual(await ait.next(it, "?"), "A")
+        # End of iteration
+        self.assertEqual(await ait.next(it, "?"), "?")
+
+    @async_test
+    async def test_next_default_async_iterable(self):
+        it = ait.iter(["A"])
+        self.assertEqual(await ait.next(it, "?"), "A")
+        # End of iteration
+        self.assertEqual(await ait.next(it, "?"), "?")
+
     # aioitertools.list()
 
     @async_test
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/tests/itertools.py 
new/aioitertools-0.8.0/aioitertools/tests/itertools.py
--- old/aioitertools-0.7.1/aioitertools/tests/itertools.py      2020-11-09 
04:47:30.139533000 +0100
+++ new/aioitertools-0.8.0/aioitertools/tests/itertools.py      2021-08-05 
04:22:56.567801200 +0200
@@ -695,6 +695,33 @@
                 await ait.next(it)
 
     @async_test
+    async def test_tee_propagate_exception(self):
+        class MyError(Exception):
+            pass
+
+        async def gen():
+            yield 1
+            yield 2
+            raise MyError
+
+        async def consumer(it):
+            result = 0
+            async for item in it:
+                result += item
+            return result
+
+        it1, it2 = ait.tee(gen())
+
+        values = await asyncio.gather(
+            consumer(it1),
+            consumer(it2),
+            return_exceptions=True,
+        )
+
+        for value in values:
+            self.assertIsInstance(value, MyError)
+
+    @async_test
     async def test_zip_longest_range(self):
         a = range(3)
         b = range(5)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/aioitertools-0.7.1/aioitertools/tests/more_itertools.py 
new/aioitertools-0.8.0/aioitertools/tests/more_itertools.py
--- old/aioitertools-0.7.1/aioitertools/tests/more_itertools.py 2020-11-09 
04:47:29.533481100 +0100
+++ new/aioitertools-0.8.0/aioitertools/tests/more_itertools.py 2021-08-05 
04:22:56.383290300 +0200
@@ -15,7 +15,7 @@
 
 async def _empty() -> AsyncIterable[int]:
     return
-    yield 0  # pylint: disable=unreachable
+    yield 0
 
 
 class MoreItertoolsTest(TestCase):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/aioitertools/types.py 
new/aioitertools-0.8.0/aioitertools/types.py
--- old/aioitertools-0.7.1/aioitertools/types.py        2020-11-09 
04:47:28.931515000 +0100
+++ new/aioitertools-0.8.0/aioitertools/types.py        2021-08-05 
04:22:56.181237700 +0200
@@ -29,3 +29,4 @@
 Accumulator = Union[Callable[[T, T], T], Callable[[T, T], Awaitable[T]]]
 KeyFunction = Union[Callable[[T], R], Callable[[T], Awaitable[R]]]
 Predicate = Union[Callable[[T], object], Callable[[T], Awaitable[object]]]
+MaybeAwaitable = Union[T, Awaitable[T]]
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/docs/_static/custom.css 
new/aioitertools-0.8.0/docs/_static/custom.css
--- old/aioitertools-0.7.1/docs/_static/custom.css      2020-05-01 
03:16:20.685631300 +0200
+++ new/aioitertools-0.8.0/docs/_static/custom.css      2021-05-16 
22:28:42.578924400 +0200
@@ -17,4 +17,8 @@
 div.omnilib-badges a:hover {
     color: #777;
     border: none;
-}
\ No newline at end of file
+}
+
+dl.class, dl.function, dl.attribute {
+    margin-bottom: 15px;
+}
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/docs/conf.py 
new/aioitertools-0.8.0/docs/conf.py
--- old/aioitertools-0.7.1/docs/conf.py 2020-05-01 03:20:29.020955000 +0200
+++ new/aioitertools-0.8.0/docs/conf.py 2021-08-05 03:54:56.994592200 +0200
@@ -35,6 +35,14 @@
     "sphinx.ext.intersphinx",
 ]
 
+autodoc_default_options = {
+    "show-inheritance": True,
+    "members": True,
+    "inherited-members": True,
+}
+autodoc_member_order = "bysource"
+autodoc_typehints = "description"
+
 # Add any paths that contain templates here, relative to this directory.
 templates_path = ["_templates"]
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/makefile 
new/aioitertools-0.8.0/makefile
--- old/aioitertools-0.7.1/makefile     2020-11-09 00:25:34.085005300 +0100
+++ new/aioitertools-0.8.0/makefile     2021-05-16 23:04:10.655338300 +0200
@@ -22,7 +22,7 @@
        python -m black aioitertools
 
 lint:
-       python -m pylint --rcfile .pylint aioitertools
+       python -m flake8 aioitertools
        python -m usort check aioitertools
        python -m black --check aioitertools
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/pyproject.toml 
new/aioitertools-0.8.0/pyproject.toml
--- old/aioitertools-0.7.1/pyproject.toml       2020-11-09 04:54:38.147944200 
+0100
+++ new/aioitertools-0.8.0/pyproject.toml       2021-03-07 00:15:44.518752300 
+0100
@@ -8,7 +8,7 @@
 author-email = "[email protected]"
 description-file = "README.md"
 home-page = "https://aioitertools.omnilib.dev";
-requires = ["typing_extensions>=3.7"]
+requires = ["typing_extensions>=3.7; python_version < '3.8'"]
 requires-python = ">=3.6"
 classifiers = [
     "Development Status :: 4 - Beta",
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/requirements-dev.txt 
new/aioitertools-0.8.0/requirements-dev.txt
--- old/aioitertools-0.7.1/requirements-dev.txt 2020-11-09 04:44:53.892360200 
+0100
+++ new/aioitertools-0.8.0/requirements-dev.txt 2021-08-05 03:56:49.667648300 
+0200
@@ -1,10 +1,10 @@
-attribution==1.4.0
-black==20.8b1
-codecov==2.1.10
-coverage[toml]==5.3
-flit==3.0.0
-mypy==0.790
-pylint==2.4.4  # pyup: <2.5
-sphinx==3.3.0
-usort==0.6.0
+attribution==1.5.2
+black==21.7b0
+codecov==2.1.11
+coverage[toml]==5.5
+flake8==3.9.2
+flit==3.2.0
+mypy==0.910
+sphinx==4.1.1
+usort==0.6.2
 git+https://github.com/miyakogi/m2r@66f4a5a500cdd9fc59085106bff082c9cadafaf3
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/requirements.txt 
new/aioitertools-0.8.0/requirements.txt
--- old/aioitertools-0.7.1/requirements.txt     2020-05-06 04:47:36.350556000 
+0200
+++ new/aioitertools-0.8.0/requirements.txt     2021-03-07 00:15:44.519299500 
+0100
@@ -1 +1 @@
-typing_extensions>=3.7
\ No newline at end of file
+typing_extensions>=3.7;python_version<"3.8"
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aioitertools-0.7.1/setup.py 
new/aioitertools-0.8.0/setup.py
--- old/aioitertools-0.7.1/setup.py     1970-01-01 01:00:00.000000000 +0100
+++ new/aioitertools-0.8.0/setup.py     1970-01-01 01:00:00.000000000 +0100
@@ -9,17 +9,17 @@
 package_data = \
 {'': ['*']}
 
-install_requires = \
-['typing_extensions>=3.7']
+extras_require = \
+{":python_version < '3.8'": ['typing_extensions>=3.7']}
 
 setup(name='aioitertools',
-      version='0.7.1',
+      version='0.8.0',
       description='itertools and builtins for AsyncIO and mixed iterables',
       author='John Reese',
       author_email='[email protected]',
       url='https://aioitertools.omnilib.dev',
       packages=packages,
       package_data=package_data,
-      install_requires=install_requires,
+      extras_require=extras_require,
       python_requires='>=3.6',
      )

Reply via email to