Issue #29198: add AsyncGenerator (Jelle Zijlstra)

This commit is contained in:
Guido van Rossum 2017-01-18 13:10:31 -08:00
parent 3c268be885
commit e9ed560fce
2 changed files with 51 additions and 1 deletions

View File

@ -1735,6 +1735,23 @@ class CollectionsAbcTests(BaseTestCase):
with self.assertRaises(TypeError):
typing.Generator[int, int, int]()
@skipUnless(PY36, 'Python 3.6 required')
def test_async_generator(self):
ns = {}
exec("async def f():\n"
" yield 42\n", globals(), ns)
g = ns['f']()
self.assertIsSubclass(type(g), typing.AsyncGenerator)
@skipUnless(PY36, 'Python 3.6 required')
def test_no_async_generator_instantiation(self):
with self.assertRaises(TypeError):
typing.AsyncGenerator()
with self.assertRaises(TypeError):
typing.AsyncGenerator[T, T]()
with self.assertRaises(TypeError):
typing.AsyncGenerator[int, int]()
def test_subclassing(self):
class MMA(typing.MutableMapping):
@ -1804,6 +1821,31 @@ class CollectionsAbcTests(BaseTestCase):
self.assertIsSubclass(G, collections.Iterable)
self.assertNotIsSubclass(type(g), G)
@skipUnless(PY36, 'Python 3.6 required')
def test_subclassing_async_generator(self):
class G(typing.AsyncGenerator[int, int]):
def asend(self, value):
pass
def athrow(self, typ, val=None, tb=None):
pass
ns = {}
exec('async def g(): yield 0', globals(), ns)
g = ns['g']
self.assertIsSubclass(G, typing.AsyncGenerator)
self.assertIsSubclass(G, typing.AsyncIterable)
self.assertIsSubclass(G, collections.AsyncGenerator)
self.assertIsSubclass(G, collections.AsyncIterable)
self.assertNotIsSubclass(type(g), G)
instance = G()
self.assertIsInstance(instance, typing.AsyncGenerator)
self.assertIsInstance(instance, typing.AsyncIterable)
self.assertIsInstance(instance, collections.AsyncGenerator)
self.assertIsInstance(instance, collections.AsyncIterable)
self.assertNotIsInstance(type(g), G)
self.assertNotIsInstance(g, G)
def test_subclassing_subclasshook(self):
class Base(typing.Iterable):

View File

@ -51,7 +51,8 @@ __all__ = [
# AsyncIterable,
# Coroutine,
# Collection,
# ContextManager
# ContextManager,
# AsyncGenerator,
# Structural checks, a.k.a. protocols.
'Reversible',
@ -1900,6 +1901,13 @@ class Generator(Iterator[T_co], Generic[T_co, T_contra, V_co],
"create a subclass instead")
return _generic_new(_G_base, cls, *args, **kwds)
if hasattr(collections_abc, 'AsyncGenerator'):
class AsyncGenerator(AsyncIterator[T_co], Generic[T_co, T_contra],
extra=collections_abc.AsyncGenerator):
__slots__ = ()
__all__.append('AsyncGenerator')
# Internal type variable used for Type[].
CT_co = TypeVar('CT_co', covariant=True, bound=type)