liveBook · Manning

Awaitable

As explained in Python Concurrency with asyncio

An awaitable is a Python object that can be supplied to await and produces a result when its asynchronous computation completes.

An awaitable is an object that can follow Python’s await keyword and eventually produce a result. Awaiting pauses the containing coroutine until the operation finishes, then resumes it with the result. section 2.1.2 section 2.5.2

Awaitables include several related asyncio objects:

  • Coroutines and futures can be awaited; tasks extend futures and combine a coroutine with a future holding its eventual result or exception. section 2.5 section 2.5.2
  • The Awaitable abstract base class defines __await__. Objects implementing __await__ can be used in an await expression. section 2.5.2
  • Awaiting does not automatically make sequential code concurrent: each await can simply pause and resume in order. section 2.1.2

Awaiting coroutine results

An async main function can await add_one(1) and add_one(2), assign the returned values, and print them. The parent coroutine pauses at each await and resumes when the called coroutine completes. section 2.1.2

A custom awaitable

A CustomFuture implements __await__. While incomplete, its iterator yields itself so an event loop can check again later; after set_result supplies a value, awaiting returns that value. section 14.5.3

Listing 14.8 A custom future implementation
class CustomFuture:
 
    def __init__(self):
        self._result = None
        self._is_finished = False
        self._done_callback = None
 
    def result(self):
        return self._result
 
    def is_finished(self):
        return self._is_finished
 
    def set_result(self, result):
        self._result = result
        self._is_finished = True
        if self._done_callback:
            self._done_callback(result)
 
    def add_done_callback(self, fn):
        self._done_callback = fn
 
    def __await__(self):
        if not self._is_finished:
            yield self
        return self.result()

Inspect a minimal custom future with result state, completion callbacks, and an __await__ method. section 14.5.3

How Python Concurrency with asyncio covers it

How deep it goes
Defines the __await__ contract and traces custom iterator behavior, but stops short of fully implementing an event loop.
Examples
Uses sequential add_one awaits and a CustomFuture whose iterator yields until set_result completes it.
What it assumes
Assumes basic async and await syntax, then develops futures, inheritance, iterators, and custom awaitable mechanics.
What you can do after
Evaluate/understand which objects await accepts and how custom awaitables signal incomplete and completed results.
How it connects
Connects coroutines, tasks, futures, generators, and the event loop through awaiting and iterator-based suspension.

Related concepts

This explainer was generated by Manning's knowledge graph from the text of Python Concurrency with asyncio. The section links point to the parts of the book it draws on.