asyncutils: makes async straightforward and enjoyable

PyPI package name: asyncutils

asyncutils is a Python library which, as the name suggests, contains helpful routines and types for asynchronous programming applications, organized under various submodules. It offers a simple and intuitive API that abstracts away headaches stemming from Python’s async quirks, and a colourful command line interface.

Installation

You are advised to ensure that your package manager is updated to the latest version as follows:

# uv (preferred for modernity, speed and compatibility with this project)
uv self update # may not work if uv was installed with pip
pip install -U uv # in that case
pip install -U pip # pip
pip install -U pipx # pipx
# conda
conda update conda anaconda
conda update --all # optional
poetry self update # poetry
pip install -U pdm # pdm
pip install -U pipenv # pipenv

Optionally make and activate a virtual environment:

uv venv # uv
pipenv shell # pipenv
poetry shell # poetry
hatch shell # hatch
python -m venv .venv # standard library
virtualenv venv # virtualenv
# conda
conda create --name asyncutils
conda activate asyncutils
# pyenv-virtualenv
pyenv virtualenv 3.14.6 asyncutils
pyenv activate asyncutils
# manual activation (venv, virtualenv):
. .venv/bin/activate # bash/zsh
. .venv/bin/activate.fish # fish
. .venv/bin/activate.csh # (t)csh

Next, install py-asyncutils:

# recommended: uv
uv pip install py-asyncutils==1.1.0
uv pip install git+https://github.com/jonathandung/asyncutils.git # directly from source
# for development, after:
git clone https://github.com/jonathandung/asyncutils.git
cd asyncutils
# you have the three options below:
uv pip install -e .
make install
make install-silent # no clutter
# the last two options need GNU Make on Unix-like systems, but the Windows version points to a batch file.
# uv is invoked under the hood and installed if absent; pip is not needed!

other installation pathways:

pip install py-asyncutils==1.1.0 # pip
pip install git+https://github.com/jonathandung/asyncutils.git # directly from source
conda install -c conda-forge py-asyncutils=1.1.0 # conda
# alternatively:
conda config --add channels conda-forge
conda config --set channel_priority strict
conda install py-asyncutils==1.1.0
pipx install py-asyncutils==1.1.0 # pipx
poetry add py-asyncutils@1.1.0 # poetry
pdm add py-asyncutils==1.1.0 # pdm
pipenv install py-asyncutils==1.1.0 # pipenv
# no package manager (needs Python and the build and installer packages)
python -m build # generate sdist and wheel in dist/
python -m installer dist/*.whl # install from the wheel

Note

We will never add setup.py, since only pyproject.toml is the modern way to go.

After this, as long as you have the python Scripts (Windows) or bin (otherwise) directory on PATH, asyncutils and autils will be made available as entry points to the asyncutils CLI, which can also be called with a typical and perhaps more familiar python -m asyncutils.

Extras

The all extra includes the dependencies for development, which are not required for normal usage. To install with extras, use the syntax appropriate for your package manager as shown in the installation instructions above.

The extras are listed below for reference:

  • all: All the extras combined

  • dev: Packages one would want installed for development; superset of docs, themes, json5, test, tools, and includes pre-commit as well. Notably, ruff and ty are absent because they should be installed with and managed by uv.

  • docs: Documentation dependencies, including Sphinx and some of its plugins, along with sphinx-lint

  • executors: All the libraries implementing executors this module supports, except distributed, since that is much too specialized and heavy.

  • json5: The Cython-accelerated JSON5 parser, specifically used to read format.json5 in tests.

  • pconf: Dependencies to parse configuration files in Hjson, JSONC, JSON5, and YAML formats

  • ptw: Monitor test failures on the command line while editing code through pytest-watch

  • test: Test dependencies, including pytest and related plugins

  • themes: Sphinx themes, including furo and sphinx-book-theme, used in the Read the Docs and GitHub Pages builds respectively; superset of docs.

Configuration

Environment Variables

The below environment variables directly affect what this library does, mostly in its console, and by extension, the command line:

AUTILSCFGPATH

Absolute path to a configuration file

AUTILSTESTMAXFAIL

Maximum number of failed tests before pytest exits early; default 3

FORCE_COLOR

Force coloured output to be used; overrides TERM=dumb but emits a warning, since this is probably not meant

Attention

FORCE_COLOR, NO_COLOR and TERM control both the argument parser and the PyREPL console.

NO_COLOR

Force coloured output to be disabled; overrides FORCE_COLOR

Note

The override is an arbitrary Python convention. It differs in other languages and frameworks.

PYTHON_BASIC_REPL

Use the pre-3.13 REPL if set and not empty, even if the newer REPL may be available

Important

The console will set this variable to “1” when it sees TERM=dumb as long as -E is not passed to the Python interpreter.

PYTHONSTARTUP

Decode the file here with tokenize and execute as a Python source file, making its symbols accessible from the console

TERM

Turn off smart terminal features, including ANSI colour sequences, when set to “dumb”

Note

The argument parser does not consider PYTHON_COLORS, but the coloured edition of the console, which uses _colorize under the hood, may. To avoid this inconsistency, do not use it to customize asyncutils’s colouring.

Note

Below Python 3.13, the output of the REPL does not highlight language keywords, only the prompt.

See also

Colour control

detailing how Python itself handles the colour-related environment variables above

Arguments to Python that are considered

Some arguments consumed by the Python interpreter are also taken into account by the library:

  • -E - Omit the execution of PYTHONSTARTUP in the console namespace and the query of PYTHON_BASIC_REPL

  • -I - Implies -E (sys.flags enforces this relationship out-of-the-box; documented here for completeness)

  • -i - Always make the console interactive even if standard input is not a TTY

    Warning

    A piped standard input will cause deadlocks or fail for most shells, and this flag might worsen the situation. It is thus declared experimental and unstable; you might see this anomaly vanish after a single patch version, or in a push that does not even bump the patch.

  • -q - To the REPL, python -q is equivalent to asyncutils -q

Tip

Even if python -S is used, which indeed does not load site as normal, the exit, quit, help, copyright, credits and license commands will still work as normal in the console since they are implemented natively, with the help of _sitebuiltins. This is attributable to a PyREPL quirk or feature. However, accessing them in any fashion other than a bare statement will cause NameError to be thrown. There is also a clear command to clear the terminal screen that will fail similarly, but that is not related to -S.

See also

Miscellaneous command-line args

authoritative source from the official Python docs

Basic Customization

An extensible, two-part configuration system is in place.

The first, frozen part includes aspects such as where to output logging, customizing the underlying executor type used, and setting a seed for random number generation using AUTILSCFGPATH.

AUTILSCFGPATH is read at the first import of this library, and the configuration is loaded and applied immediately. Errors will be thrown as appropriate if the file is not found or contains values of the incorrect type, after the library tries its best to coerce the types, but you may see a raw ModuleNotFoundError if the library cannot be located or executed.

Automatic discovery of config files, as in other libraries or command-line tools, is not supported, because there is no standard location for it and determining a precedence for the different allowed file extensions would be arbitrary, non-trivial and difficult to maintain.

The options are shown below, along with their default values and descriptions:

config file format
/* This file describes the intended format of the json files whose paths can be set as AUTILSCFGPATH to configure the behaviour of this module.
The values associated with the keys are their defaults.
Some keys can have various types, as detailed by the comments attached. */
{
  logging_to: "STDERR",
  // string file path or integer file descriptor, to which the logging is dumped
  // corresponds to -l/--log-to
  no_log: false,
  // disable logging; conflicts with logging_to if true
  // corresponds to -n/--no-log
  V: 0, // increase logging verbosity; corresponds to -V
  Q: 0, // decrease logging verbosity; corresponds to -Q
  // V and Q are not respected when running the console
  executor: "thread",
  /* choose the PEP 3148 executor class to use when required
  refer to `tools.get_cmd_help` for possible values
  corresponds to -e/--executor/-c/--custom-executor */
  quiet: false,
  // ask the console not to show introductory and closing text
  // corresponds to -q/--quiet
  basic_repl: false,
  // run the console without any _pyrepl wrapping; not recommended
  // corresponds to -b/--basic-repl
  max_memory_errors: 3,
  // protect resource integrity by exiting the console on the MemoryError at the index after this
  // corresponds to -m/--max-memory_errors
  debug: false,
  // turn on debug mode by entering the global debug context manager
  // incurs performance penalty due to excessive logging, so do not use outside testing
  // corresponds to -d/--debug
  load_all: false,
  // load all submodules when the console starts; corresponds to -p/--load-all
  seed: null,
  // string, integer, float or byte string literal to seed the module-global random device
  // corresponds to -s/--seed
  pdb: false,
  // whether to bring the user into the pdb debugger on SystemExit with non-zero status from the console; corresponds to -P/--pdb
  next_config: null,
  /* string file path to the json to be used for the next time this module is to be configured
  This key may be useful for temporary configurations that want to be automatically unset and replaced with a main configuration.
  If null, the environment variable is unset entirely after reading this config.
  Cycles can be created to switch between flags periodically.
  Ensure AUTILSCFGPATH is set to a valid file path if you keep encountering errors, since it could have been incorrectly set
  in a previous config. By that logic, you should also remember to update this correctly when the config file is moved. */
  context: { // configures individual submodules (contextual constants)
    /* Essentially maps submodule names to objects like {utility1: {key1: value1, key2: value2, ...}}, utility2: {...}};
    or if the utility has only one configurable parameter, there will be a key at the top level of a mapping above,
    and the keys will be sorted alphabetically. */
    altlocks: {
      circuit_breaker: {
        default_max_fails: 3,
        default_max_half_open_calls: 5,
        default_reset: 30.0,
      },
      dynamic_throttle: {
        default_jitter: 0.2,
        default_lbound: 0.25,
        default_lfactor: 0.75,
        default_max_rate: 100.0,
        default_min_rate: 1e-2,
        default_ubound: 0.75,
        default_ufactor: 1.25,
        default_window: 100,
      }
    },
    base: {
      event_loop_base_flags: 0,
      aiter_to_gen: {
        default_allow_futures: true,
        default_strict: false
      },
      iter_to_agen: {
        default_may_create_executor: false,
        default_strict: false,
        default_use_existing_executor: false
      }
    },
    buckets: {
      token_bucket_default_consume_tokens: 1.0,
      leaky_bucket: {
        adjmap: [
          [256, [0.15, 1.1, 0.85, 0.9]],
          [128, [0.23, 1.2, 0.77, 0.81]],
          [0, [0.3, 1.4, 0.7, 0.73]]
        ],
        default_acquire_tokens: 1.0,
        default_ext_can_set_factor: true,
        default_max_factor: 10.0,
        default_min_factor: 0.1,
        default_wait_for_tokens_tokens: 1.0,
        wait_for_tokens_tick: 0.1
      }
    },
    channels: {
      event_bus: {
        default_max_concurrent: 64,
        publish_default_safe: true,
        stream_default_buffer_size: 100,
        stream_default_item_timeout: 3.0,
        stream_default_timeout: 5.0
      },
      observable_default_ntimes_n: 1,
      rendezvous_maintenance_interval: 30.0
    },
    compete: {convert_to_coro_iter_default_skip_invalid: true},
    events: {
      event_with_value: {
        default_max_hist: 128,
        default_recent: 5.0
      }
    },
    func: {
      benchmark: {
        default_times: 3,
        default_warmup: 0
      },
      retry: {
        default_backoff: 2.0,
        default_delay: 0.5,
        default_jitter: 0.2,
        default_max_delay: 30.0,
        default_tries: 3
      },
      timer_default_precision: 7
    },
    io: {
      memory_mapped_io_manager: {
        default_checksum_alg: null, // a string
        default_minimize_writes: true
      }
    },
    iters: {
      afreivalds_default_k: 2,
      aonline_sorter_default_slow: false,
      aunzip: {
        default_max_qsize: 64,
        default_put_batch: 16
      },
      merge_default_max_qsize: 0,
      tee: {
        default_put_exc: true,
        default_max_qsize: 32
      }
    },
    locks: {
      advanced_rate_limit_default_tokens: 1.0,
      dynamic_bounded_semaphore_default_value: 1,
      priority_semaphore_default_value: 1
    },
    locksmiths: {locksmith_base_default_timeouts: [1.0, 0.1, null]},
    misc: {
      gather_with_limited_concurrency_default_max_concurrent: 8,
      background_refresh_cache: {
        default_refresh: 15.0,
        default_ttl: 60.0
      }
    },
    networking: {
      line_protocol_default_buffer_size: 4096,
      socket_transport_limits: [2048, 8192]
    },
    pools: {
      advanced_pool: {
        default_max_workers: 5,
        default_min_workers: 1,
        threshold_hi: 1.5,
        threshold_lo: 0.5
      },
      connection_pool: {
        default_max_life: 3600.0,
        default_max_size: 10,
        default_min_size: 1,
        maintenance_interval: 30.0
      }
    },
    processors: {
      batch_processor: {
        default_max_size: 128,
        default_max_time: 1.0
      },
      bounded_batch_processor: {
        default_batch_size: 10,
        default_max_concurrent: 5
      },
      bulkhead: {
        default_max_queue: 32,
        default_max_rej: -1
      }
    },
    queues: {
      password_queue: {
        default_get_from: "password",
        default_put_from: "password"
      }
    },
    rwlocks: { // cspell:disable
      aging_rwlock: {
        default_read_priority_factor: -1.0,
        default_write_priority_factor: -1.0
      },
      rwlock_default_prefer_writers: true
    }, // cspell:enable
    signals: {wait_for_signals_default_signals: [2, 15]},
    util: {
      dual_context_manager: {
        default_may_create_executor: false,
        default_strict: false,
        default_use_existing_executor: true
      },
      semaphore_default_value: 1
    }
  }
}

New options will likely be added in the future, but every current option is considered stable and has a corresponding default value.

The above keys have a near one-to-one correspondence with the command line arguments, as the comments below each key explain. Use asyncutils -? to see detailed CLI usage.

The config file can be written in the below formats, listed with the third-party libraries they require if any:

Format

File extension

Module name

PyPI package name

JSON

.json

json

TOML

.toml

tomllib

YAML

.yaml, .yml

yaml

PyYAML

JSONC

.jsonc

jsonc

json-with-comments

JSON5

.json5

pyjson5

pyjson5

Hjson

.hjson

hjson

hjson

XML

.xml

xmltodict

xmltodict

Be especially careful with using XML, because it is verbose, overkill and not recommended for use, especially with many simpler alternatives.

See also

CVE-2025-9375

a vulnerability of the XMLGenerator class from the standard library used by xmltodict without input sanitization

Note

This exploit is disputed by the maintainers of the project.

the CVE database

for any new vulnerabilities

Important

To write the config in each format, adhere to the exact analogue of the nested dictionary structure shown in format.json5 in the chosen language.

Tip

The dumps() function from the module corresponding to the format, if any (following the json API), may help you to obtain this skeleton approximately.

Warning

The exact parsing method used by this module may allow object nesting deviating from that shown, but you should still strictly adhere to it.

Tip

To ensure all supported formats can be parsed, install the pconf extra.

INI is not supported because it is outdated and lacks strong typing, meaning all values are interpreted as strings.

It is currently possible to associate file extensions not shown above with other libraries providing a load function taking a file object and returning a dictionary, by modifying the map from file extensions to names of corresponding modules in _internal/unparsed.py called Z. However, it is believed that the options offered are versatile enough to fit every individual need.

Contextual “Constants”

You can see that the json also includes many submodule names as keys; this is the second, contextual part of the configuration. It is thread-safe, async-safe and mutable, thanks to contextvars. The sheer magnitude of options makes them infeasible to include as command line arguments.

By convention, they are called contextual constants since no code in this library is expected to change their values, only reading from them to determine things from dynamic default arguments to frequencies of background tasks and internal thresholds.

One may find it useful to alter the context dynamically without creating a new context. This can be achieved by calling Context.update().

See also

Context.copy()

Context.replace()

Context.replace_from_dct()

It is advisable to call these methods, each of which leaves the original context alone and derives a new one from it.

__copy__() and __replace__() are also implemented to help copy.copy() and copy.replace() respectively.

It is even better to use NonReusableLocalContext, which returns a one-time context manager, or the convenience method Context.ascurctx() on context objects that wraps it.

For more detailed documentation on context usage, see the context page.

Tip

You can think of the Context class as similar to decimal.Context, but with different methods and attributes and customizing an entire module instead of quirks and traps of the operations of a single class.

Audit events table

This page details all events raised by this library through sys.audit() and the corresponding arguments.

This module takes care not to expose sensitive information in the events, so that the audit hooks often only see the fully qualified name of the type of some handled object rather than the object itself.

For consistency and namespace integrity, all audit event names begin with ‘asyncutils’, and are often exactly the fully qualified name of the function being called.

See the official documentation for sys.audit() and sys.addaudithook() on how to listen to these events, as well as channels.EventBus, which is capable of triggering mass publications to async subscribers for audit events efficiently.

Also see the standard library audit event table, from which the inclusion and format of this table take inspiration.

Audit events

Audit event

Arguments

Description

asyncutils/create_executor

fname: str

Raised when asyncutils creates an executor, type dictated by configuration. fname is of the form ‘submodule.function’.

asyncutils/get_loop_and_set

loop: AbstractEventLoop

Raised when asyncutils retrieves an event loop loop, creating one if necessary, and sets it as the event loop for the current thread if not already set.

asyncutils/recurse_dirs

cwd: Path

Raised when the environment variable pointing to a config file is not set, and library resorts to beginning to traverse the parents of the current working directory sequentially to look for pyproject.toml files with a (possibly empty) [tool.asyncutils] section.

asyncutils/try_config

level: int

Raised when asyncutils finds a file named pyproject.toml in the level-th parent of the current working directory (but hasn’t parsed it yet).

asyncutils/read_config

cfg_path: str

Raised when asyncutils reads its configuration file expected to be in json format at cfg_path (not guaranteed to be absolute).

asyncutils/discontinue_config

cfg_path: str

Raised when asyncutils no longer uses the configuration file at cfg_path, since its next_config key corresponds to null or equivalent.

asyncutils/set_next_config

old_path: str, new_path: str

Raised when asyncutils changes its configuration file from that at old_path to that at new_path, as dictated by the next_config field.

asyncutils.altlocks.UniqueResourceGuard

rtyp: str

Raised when altlocks.UniqueResourceGuard is instantiated, with rtyp being the fully qualified name of the type of the resource being guarded, including its module.

asyncutils.altlocks.CircuitBreaker

name: str, max_fails: int

Raised when altlocks.CircuitBreaker is instantiated, with name being its name and max_fails the number of consecutive failures that will cause the circuit to open.

asyncutils.altlocks.CircuitBreaker.__call__

name: str, fname: str

Raised when a altlocks.CircuitBreaker of name name is applied on a function with name fname.

asyncutils.base.safe_cancel_batch

ityp: str

Raised when base.safe_cancel_batch() is called on the (possibly async) iterable with exact type of name ityp.

asyncutils.base.iter_to_agen

tname: str

Raised when base.iter_to_agen() is called on an iterable of type with name tname.

asyncutils.base.aiter_to_gen

tname: str

Raised when base.aiter_to_gen() is called on an async iterable of type with name tname.

asyncutils.buckets.TokenBucket

rate: float, capacity: float

Raised when buckets.TokenBucket is instantiated, with rate being the token refill rate and capacity the maximum number of tokens.

asyncutils.buckets.LeakyBucket

capacity: float, leak: float

Raised when buckets.LeakyBucket is instantiated, with capacity being the maximum number of tokens and leak the leak rate.

asyncutils.channels.Observable

maxsize: int|None

Raised when channels.Observable is instantiated, with maxsize being the maximum number of subscribers or None if there is no such limit.

asyncutils.channels.EventBus

name: str, addr: int

Raised when channels.EventBus is instantiated, with name being its name or None if not passed, and addr its memory address.

asyncutils.channels.EventBus.start_audit

addr: int

Raised when the start_audit() method of channels.EventBus is called, with the memory address of the instance as argument.

asyncutils.channels.EventBus.stop_audit

addr: int

Raised when the stop_audit() method of channels.EventBus is called, with the memory address of the instance as argument.

asyncutils.channels.EventBus.event_stream

addr: int, event_type: str|None

Raised when the event_stream() method of channels.EventBus is called. addr is the memory address of the instance, and event_type is the event type the stream was opened for or None for catch-all streams.

asyncutils.cli.run

Raised with no arguments when the command-line interface of this library is first invoked through the entry point asyncutils, even if just asking for the version or help.

asyncutils.compete.first_completed/start

ntasks: int

Raised when compete.first_completed() is called, with ntasks coroutines.

asyncutils.compete.first_completed/end

ntasks: int

Raised when compete.first_completed() finishes, with ntasks coroutines.

asyncutils.compete.race_with_callback/start

ntasks: int

Raised when compete.race_with_callback() is called, with ntasks coroutines.

asyncutils.compete.race_with_callback/end

ntasks: int

Raised when compete.race_with_callback() finishes, with ntasks coroutines.

asyncutils.compete.multi_winner_race_with_callback/start

ntasks: int

Raised when compete.multi_winner_race_with_callback() is called, with ntasks coroutines.

asyncutils.compete.multi_winner_race_with_callback/end

ntasks: int

Raised when compete.multi_winner_race_with_callback() finishes, with ntasks coroutines.

asyncutils.console.AsyncUtilsConsole.run

addr: int

Raised when the run() method of an instance of console.AsyncUtilsConsole at addr is called.

asyncutils.exceptions.unnest

n: int

Raised when exceptions.unnest() is called, with n being a sloppy lower bound on the number of exception( group)s.

asyncutils.exceptions.unnest_reverse

n: int

Raised when exceptions.unnest_reverse() is called, with n being a sloppy lower bound on the number of exception( group)s.

asyncutils.exceptions.raise_exc

exc: BaseException

Raised when exceptions.raise_exc() is about to raise exc, such that hooks may process the instance or perform validation outside the scope of exceptions.prepare_exception().

asyncutils.func.benchmark

fname: str, total_rounds: int

Raised when func.benchmark() is called, with fname being the name of the function being benchmarked, and total_rounds the total number of rounds to be executed, including warmup rounds.

asyncutils.func.RateLimited

fname: str, calls: int, period: float

Raised when a func.RateLimited is instantiated, with fname being the name of the function being rate limited, calls the number of calls allowed every period seconds.

asyncutils.futures.AsyncCallbacksFuture/schedule_callbacks

addr: int

Raised when the exact instance of futures.AsyncCallbacksFuture at address addr schedules its sync and async callbacks.

asyncutils.futures.AsyncCallbacksTask/schedule_callbacks

addr: int

The above, but for exact instances of futures.AsyncCallbacksTask.

asyncutils.futures.TimeAwareAsyncCallbacksFuture/schedule_callbacks

addr: int

The above, but for exact instances of futures.TimeAwareAsyncCallbacksFuture.

asyncutils.futures.TimeAwareAsyncCallbacksTask/schedule_callbacks

addr: int

The above, but for exact instances of futures.TimeAwareAsyncCallbacksTask.

asyncutils.futures.UniqueCallbacksFuture/schedule_callbacks

addr: int

The above, but for exact instances of futures.UniqueCallbacksFuture.

asyncutils.futures.UniqueCallbacksTask/schedule_callbacks

addr: int

The above, but for exact instances of futures.UniqueCallbacksTask.

asyncutils.futures.TimeAwareUniqueCallbacksFuture/schedule_callbacks

addr: int

The above, but for exact instances of futures.TimeAwareUniqueCallbacksFuture.

asyncutils.futures.TimeAwareUniqueCallbacksTask/schedule_callbacks

addr: int

The above, but for exact instances of futures.TimeAwareUniqueCallbacksTask.

asyncutils.iotools.double_ended_pipe

reader1: int, writer1: int, reader2: int, writer2: int

Raised when iotools.double_ended_text_pipe() or iotools.double_ended_binary_pipe() is called, with the file descriptors of the reader and writer ends of both pipes as arguments.

asyncutils.iters.aonline_sorter

addr: int

Raised when iters.aonline_sorter is called on an (async) iterable with memory address addr.

asyncutils.iters.extract

tname: str

Raised when iters.extract() is called on an iterable, the type of which has full name tname.

asyncutils.iters.aintersend

tname1: str, tname2: str

Raised when iters.aintersend() is called on two async generators, the types of which have full names tname1 and tname2 respectively.

asyncutils.iters.asendstream

tname1: str, tname2: str

Raised when iters.asendstream() is called, the full name of the type of the async generator being tname1 and that of the (async) iterable being tname2.

asyncutils.iters.acat

first: Any

Raised when iters.acat() is called, first being the item yielded to start the async generator.

asyncutils.iters.aforever

Raised when iters.aforever() is called.

asyncutils.locksmiths.LocksmithBase.force

saddr: int, laddr: int

Raised when locksmiths.LocksmithBase.force() is called, with the memory addresses of the locksmith instance and the lock being forced in that order as arguments. Audit hooks can choose to block the force by raising or take action in response.

asyncutils.misc.CacheWithBackgroundRefresh

ttl: float, refresh: float

Raised when misc.CacheWithBackgroundRefresh is instantiated, with ttl being the time to live of cache entries and refresh the time before expiry at which background refreshes are triggered.

asyncutils.networking.LineProtocol

Raised when networking.LineProtocol is instantiated.

asyncutils.networking.CRLFProtocol

Raised when networking.CRLFProtocol is instantiated.

asyncutils.networking.CRProtocol

Raised when networking.CRProtocol is instantiated.

asyncutils.networking.LFProtocol

Raised when networking.LFProtocol is instantiated.

asyncutils.networking.SocketTransport

Raised when networking.SocketTransport is instantiated.

asyncutils.queues.password_queue

get_from: str|None, put_from: str|None

Raised when queues.password_queue() is called, with the names of the variables from which passwords for get and put operations will be retrieved in the caller scope if they are protected, or None if they are not protected. Of course, the audit hooks do not see the passwords themselves.

asyncutils.queues.SmartQueue.push

addr: int, pushed: T, popped: T

Raised when the push() method of an exact instance of queues.SmartQueue with items of type T is called and the queue is full, such that an item must be popped, to avoid data loss. addr is the memory address of the instance, pushed the item being pushed, and popped the item being popped.

asyncutils.queues.SmartQueue.transaction/start

addr: int

Raised when the transaction() method of an exact instance of queues.SmartQueue is called, with addr being the memory address of the instance.

asyncutils.queues.SmartQueue.transaction/end

addr: int

Raised when the context manager returned by the transaction() method of an exact instance of queues.SmartQueue exits (the transaction succeeds or fails), with addr being the memory address of the instance.

asyncutils.queues.SmartQueue.map

addr: int, fname: str

Raised when the map() method of an exact instance of queues.SmartQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the transformation function.

asyncutils.queues.SmartQueue.starmap

addr: int, fname: str

Raised when the starmap() method of an exact instance of queues.SmartQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the transformation function.

asyncutils.queues.SmartQueue.filter

addr: int, fname: str

Raised when the filter() method of an exact instance of queues.SmartQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the predicate.

asyncutils.queues.SmartQueue.enumerate

addr: int

Raised when the enumerate() method of an exact instance of queues.SmartQueue is called, with addr being the memory address of the instance.

asyncutils.queues.SmartLifoQueue.push

addr: int, pushed: T, popped: T

Raised when the push() method of an exact instance of queues.SmartLifoQueue with items of type T is called and the queue is full, such that an item must be popped, to avoid data loss. addr is the memory address of the instance, pushed the item being pushed, and popped the item being popped.

asyncutils.queues.SmartLifoQueue.transaction/start

addr: int

Raised when the transaction() method of an exact instance of queues.SmartLifoQueue is called, with addr being the memory address of the instance.

asyncutils.queues.SmartLifoQueue.transaction/end

addr: int

Raised when the context manager returned by the transaction() method of an exact instance of queues.SmartLifoQueue exits (the transaction succeeds or fails), with addr being the memory address of the instance.

asyncutils.queues.SmartLifoQueue.map

addr: int, fname: str

Raised when the map() method of an exact instance of queues.SmartLifoQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the transformation function.

asyncutils.queues.SmartLifoQueue.starmap

addr: int, fname: str

Raised when the starmap() method of an exact instance of queues.SmartLifoQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the transformation function.

asyncutils.queues.SmartLifoQueue.filter

addr: int, fname: str

Raised when the filter() method of an exact instance of queues.SmartLifoQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the predicate.

asyncutils.queues.SmartLifoQueue.enumerate

addr: int

Raised when the enumerate() method of an exact instance of queues.SmartLifoQueue is called, with addr being the memory address of the instance.

asyncutils.queues.SmartPriorityQueue.push

addr: int, pushed: T, popped: T

Raised when the push() method of an exact instance of queues.SmartPriorityQueue with items of type T is called and the queue is full, such that an item must be popped, to avoid data loss. addr is the memory address of the instance, pushed the item being pushed, and popped the item being popped.

asyncutils.queues.SmartPriorityQueue.transaction/start

addr: int

Raised when the transaction() method of an exact instance of queues.SmartPriorityQueue is called, with addr being the memory address of the instance.

asyncutils.queues.SmartPriorityQueue.transaction/end

addr: int

Raised when the context manager returned by the transaction() method of an exact instance of queues.SmartPriorityQueue exits (the transaction succeeds or fails), with addr being the memory address of the instance.

asyncutils.queues.SmartPriorityQueue.map

addr: int, fname: str

Raised when the map() method of an exact instance of queues.SmartPriorityQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the transformation function.

asyncutils.queues.SmartPriorityQueue.starmap

addr: int, fname: str

Raised when the starmap() method of an exact instance of queues.SmartPriorityQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the transformation function.

asyncutils.queues.SmartPriorityQueue.filter

addr: int, fname: str

Raised when the filter() method of an exact instance of queues.SmartPriorityQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the predicate.

asyncutils.queues.SmartPriorityQueue.enumerate

addr: int

Raised when the enumerate() method of an exact instance of queues.SmartPriorityQueue is called, with addr being the memory address of the instance.

asyncutils.queues.UserPriorityQueue.push

addr: int, pushed: T, popped: T

Raised when the push() method of an exact instance of queues.UserPriorityQueue with items of type T is called and the queue is full, such that an item must be popped, to avoid data loss.

asyncutils.queues.UserPriorityQueue.transaction/start

addr: int

Raised when the transaction() method of an exact instance of queues.UserPriorityQueue is called, with addr being the memory address of the instance.

asyncutils.queues.UserPriorityQueue.transaction/end

addr: int

Raised when the context manager returned by the transaction() method of an exact instance of queues.UserPriorityQueue exits (the transaction succeeds or fails), with addr being the memory address of the instance.

asyncutils.queues.UserPriorityQueue.map

addr: int, fname: str

Raised when the map() method of an exact instance of queues.UserPriorityQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the transformation function.

asyncutils.queues.UserPriorityQueue.starmap

addr: int, fname: str

Raised when the starmap() method of an exact instance of queues.UserPriorityQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the transformation function.

asyncutils.queues.UserPriorityQueue.filter

addr: int, fname: str

Raised when the filter() method of an exact instance of queues.UserPriorityQueue is called, with addr being the memory address of the instance and fname the fully qualified name of the predicate.

asyncutils.queues.UserPriorityQueue.enumerate

addr: int

Raised when the enumerate() method of an exact instance of queues.UserPriorityQueue is called, with addr being the memory address of the instance.

asyncutils.signals.wait_for_signal

sigs: set[int]

Raised when signals.wait_for_signal() is called on signal numbers sigs. Audit hooks can modify the set, and the changes will be reflected.

asyncutils.util.sync_await

atname: str

Raised when util.sync_await() is called on an awaitable whose type is of name atname.

asyncutils.util.to_async

fname: str

Raised when util.to_async() is called on a function with name fname.

asyncutils.util.to_sync

fname: str

Raised when util.to_sync() is called on a function with name fname.

Logging

Code is bound to contain bugs, and this library is no exception. Logging is thus an important aspect of asyncutils. Users can also see what is being done under the hood and view the timestamps of significant events, without exercising advanced reflection or metaprogramming or attaching a tracer, profiler or debugger.

This module employs logging as provided by the standard library, which may contribute to a significant chunk of the boot time of this module but is much too widely used for us to find alternatives such as loguru, especially due to concerns in adding a dependency and compatibility issues.

While we also use auditing for applications where it is deemed useful to have custom behaviour programmatically triggered, we follow the DRY (don’t repeat yourself) philosophy, meaning most audit events and logs are mutually exclusive, and anything displayed in the console banner is not logged.

Tip

If logging is still desired then, an audit hook that calls the logger iff the name of the event begins with ‘asyncutils’ should be added using sys.addaudithook(), but performance may take a hit.

As to how the loquacity and output location of the logger can be altered, refer to the following snippets:

relevant portion of the stub of the config submodule
class Debugging:
    '''A context manager used to enter and exit debug mode, ensuring restoration of the original level if the level has not been modified externally within the context using :func:`set_logger_level`.'''
    @property
    def level(self) -> int: '''The current level of the :mod:`asyncutils` logger, as an integer.'''
    @property
    def orig_level(self) -> int|None: '''The original logger level as an integer, before this context was entered, or ``None`` if it was not.'''
    @property
    def orig_name(self) -> str|None: '''The original logger level name as a string, before this context was entered, or ``None`` if it was not.'''
    @property
    def entered(self) -> bool: '''Whether the context is entered.'''
    def __enter__(self) -> Self: '''Start debugging. More output is produced; where to depends on the user's own configuration, accessible via :data:`logging_to` and ``debug.level``.'''
    @overload
    def __exit__(self, exc_typ: ExcType, exc_val: BaseException, exc_tb: TracebackType, /) -> None: ...
    @overload
    def __exit__(self, exc_typ: None, exc_val: None, exc_tb: None, /) -> None: '''Stop debugging, restoring the output to its previous level if appropriate.'''
def set_logger_level(level: int) -> None: '''Set the level of the module-global logger to ``level``.'''
def get_past_logs() -> str: '''Return all stored logs as a string. Logs are stored iff :mod:`asyncutils` was started with ``-l MEMORY``, otherwise an empty string is returned.'''
debug: Final[Debugging]
'''A global instance of the :class:`Debugging` context manager. Initially entered iff the user specified ``-d`` or ``--debug`` when starting the program.'''
silent: Final[bool]
'''Whether the user requested to run the program with no banner and exit message in the REPL.'''
logging_to: Final[str]
'''The name of (i.e. possibly relative path to) the log file currently used by this library as a string, with four exceptions:

* ``'NULL'``: no logging is taking place
* ``'MEMORY'``: the logs are not going to a physical file but can be retrieved by :func:`get_past_logs`
* ``'STDOUT'``: logging is going to :data:`sys.stdout`
* ``'STDERR'``: logging is going to :data:`sys.stderr` (following the default and fallback behaviour of :mod:`logging`)'''
json-based or command-line configuration
{
  logging_to: "STDERR",
  // string file path or integer file descriptor, to which the logging is dumped
  // corresponds to -l/--log-to
  no_log: false,
  // disable logging; conflicts with logging_to if true
  // corresponds to -n/--no-log
  V: 0, // increase logging verbosity; corresponds to -V
  Q: 0, // decrease logging verbosity; corresponds to -Q
  // V and Q are not respected when running the console
  quiet: false,
  // ask the console not to show introductory and closing text
  // corresponds to -q/--quiet
  debug: false,
  // turn on debug mode by entering the global debug context manager
  // incurs performance penalty due to excessive logging, so do not use outside testing
  // corresponds to -d/--debug
}

The format of each log message as printed is “<asctime> - asyncutils - <levelname> - <message>”, where levelname is one of DEBUG, INFO, WARNING, ERROR, and CRITICAL.

Note

Though the above is stable and allows deterministic parsing of a log file, it is recommended to instead attach custom handlers to the logger, as returned by logging.getLogger('asyncutils'), using the logging API to achieve the same effect more efficiently and less hackily.

CLI Usage

This is the contents of a file to which the help command from the command-line interface is redirected, as of asyncutils v1.1.0:

usage: asyncutils [-l [FILE] | -n] [-e ETYP | -c ETYP | --thread | --process |
                  --interpreter | --loky | --loky-no-reuse | --dask |
                  --ipython | --elib-flux-cluster | --elib-flux-job |
                  --elib-slurm-cluster | --elib-slurm-job |
                  --elib-single-node | --pebble-thread | --pebble-process |
                  --deadpool] [-Q] [-V] [-q] [-b] [-m M] [-p] [-s SEED] [-d]
                  [-P] [-v] [-?]

Copyright (c) 2026 Jonathan Dung. All rights reserved.

A versatile, feature-rich library of async tools integrated into the asyncio framework, aiming to make asynchronous programming easier for everyone.
Has CLI and coloured REPL support for quick development.
On both conda and pip as py-asyncutils.

options:
  -l, --log-to [FILE]   This module uses a logger, so that post-mortem debugging can be done by inspecting the log file created.
                        When FILE, interpreted as a file descriptor if an integer, is passed, the logging output goes to a file with that name.
                        Passing 'NULL' for FILE is equivalent to specifying the --no-log option.
                        If FILE is 'MEMORY', logs are stored in memory and returned and voided whenever get_past_logs is called.
                        If FILE is 'MAKE' or no filename is passed but the option specified, an attempt is made to create a file of format 'asyncutils_log<number>.log' in the
                        current working directory for logging, for number from 1 to 4096. If you have more than 4096 log files, you should probably clean them up.
                        Log file rotation is not currently supported.
                        If FILE is 'STDOUT', log to standard output.
                        If FILE is 'STDERR', log to standard error. This is also the default behaviour and fallback if the above steps fail.
  -n, --no-log          Disable logging completely.
                        A disabled logger is still created to make subsequent logging.getLogger calls return it.
                        Thus, this option cannot avoid the cost of importing logging and instantiating the logger early on.
  -e, --executor ETYP   Choose an executor class to use when necessary depending on the value of ETYP as follows:
                        thread: Use concurrent.futures.thread.ThreadPoolExecutor. This is the default and will be used if the third-party options are passed but not installed.
                        The below options are experimental.
                        process: Use concurrent.futures.process.ProcessPoolExecutor. Use with care, since this depends on CPU architecture.
                        interpreter: Use concurrent.futures.interpreter.InterpreterPoolExecutor. May throw various errors relating to unshareable objects.
                        The below options are third-party.
                        loky_no_reuse: Use a new loky.process_executor.ProcessPoolExecutor every time.
                        loky: Reuse a loky.process_executor.ProcessPoolExecutor if possible.
                        dask: Use dask.distributed.Client, the API of which just so happens to be a superset of that of concurrent.futures executors.
                        ipython: Use ipyparallel.ViewExecutor.
                        elib_flux_cluster: Use executorlib.executor.flux.FluxClusterExecutor.
                        elib_flux_job: Use executorlib.executor.flux.FluxJobExecutor.
                        elib_slurm_cluster: Use executorlib.executor.slurm.SlurmClusterExecutor.
                        elib_slurm_job: Use executorlib.executor.slurm.SlurmJobExecutor.
                        elib_single_node: Use executorlib.executor.single.SingleNodeExecutor.
                        pebble_thread: Use pebble.pool.thread.ThreadPool.
                        pebble_process: Use pebble.pool.process.ProcessPool.
                        deadpool: Use deadpool.Deadpool.
                        There are some implementations from niche libraries (found on a PyPI-wide search using the keyword "executor") that are intentionally excluded, since
                        they either require prior configuration to be useful (as is the case with adaptive-executor), are too small (contextvars-executor), unmaintained
                        (celery-executor), too little-known (sequential-executor), rely on possibly outdated implementation details (bounded-pool-executor), have specific
                        backends seldom used for this purpose (Flask-Executor) or have completely incompatible APIs (thread-executor). In those cases, pass the fully qualified
                        name to -c and bear the potential consequences.
  -c, --custom-executor ETYP
                        Use a custom executor not included in the above options by specifying the name of an implementation.
                        Passing "package.submodule.Implementation", for example, will execute "from package.submodule import Implementation as Executor".
  --thread              Equivalent to "-e thread".
  --process             Equivalent to "-e process".
  --interpreter         Equivalent to "-e interpreter".
  --loky                Equivalent to "-e loky".
  --loky-no-reuse       Equivalent to "-e loky_no_reuse".
  --dask                Equivalent to "-e dask".
  --ipython             Equivalent to "-e ipython".
  --elib-flux-cluster   Equivalent to "-e elib_flux_cluster".
  --elib-flux-job       Equivalent to "-e elib_flux_job".
  --elib-slurm-cluster  Equivalent to "-e elib_slurm_cluster".
  --elib-slurm-job      Equivalent to "-e elib_slurm_job".
  --elib-single-node    Equivalent to "-e elib_single_node".
  --pebble-thread       Equivalent to "-e pebble_thread".
  --pebble-process      Equivalent to "-e pebble_process".
  --deadpool            Equivalent to "-e deadpool".

verbosity:
  Adjust the amount of output of this program.

  -Q                    Produce less logging output. Additive.
  -V                    Produce more logging output. Additive.

repl:
  Configure the behaviour of the Read-Eval-Print Loop of this module.

  -q, --quiet           Do not display the banner and exit message in the REPL; the -q flag can be passed to the python command directly to achieve the same effect.
  -b, --basic-repl      Do not use the console with colours and enhanced functionality from _pyrepl. Use only if you have experienced a bug with the coloured console.
  -m, --max-memory_errors M
                        The REPL will exit on the (M+1)-th MemoryError to prevent consuming too many computer resources.
                        M defaults to 3.
                        Set to a negative value to disable the threshold completely.

testing:
  Options to more conveniently test this module.

  -p, --load-all        Preload all submodules of this module. Useful for testing, but incurs noticeable performance penalty.
  -s, --seed SEED       Seed the random instance used internally by this module with SEED, which will be interpreted as an integer if possible.
  -d, --debug           Enable debug mode to produce more logging output by entering the global debug context manager. Different from -VV, since
                        the verbosity flags take effect again when the context manager is manually exited.
  -P, --pdb             Intended for developers of this library only; open the pdb debugger interface when the exit code of the console is greater than zero,
                        or an uncaught error occurs in the console execution logic itself.

metadata:
  Get basic information about this installation of asyncutils.

  -v, --version         Print the current version number of asyncutils, in the form as specified by __version__.representation, and exit.
                        Useful for checking if the installation succeeded.
  -?, -h, --help        Print this help message and exit.

Use @<filename> to insert command-line arguments from the file of that name at the exact position of this parameter.
The file should have one argument per line; this format differs from that described below.

Use the AUTILSCFGPATH environment variable to specify a path to a file of a supported type containing the default configuration.
A --config option is not offered due to the complexity of implementation and ease to revert to a default config within a one-off config.
See the possible keys in format.json5, which can be accessed using tools.get_cfg_json_format().

Note that the inner workings of this library is tightly coupled with the ever-evolving asyncio framework.
As such, it is probably incompatible with full-fledged third-party async frameworks such as curio, anyio, trio, and tornado.

Note

Generated by scripts/unix/genhelp.sh in Read the Docs latest build at 2026-07-11 10:53:59 UTC.

Usage Examples

Below are some examples of how the asyncutils module can be used, demonstrated right in the tailor-made async-native asyncutils REPL console:

>>> load_all() # A function that does the equivalent of the preprocessing done when asyncutils sees the -p/--load-all flag, fetching and executing\
all submodules immediately as opposed to finding and importing them on first attribute access; only call if testing the console out
>>> # all the code below will work regardless of the presence of the above line
>>> # example 1: Rendezvous
>>> import asyncio
>>> rdv = channels.Rendezvous[int]() # directly access the submodule object "channels" as a global
>>> # usually, types that make sense to be generic can be subscripted; see the exact parameters taken in the .pyi files
>>> (await asyncio.gather(*map(rdv.put, range(5, 10)), rdv.exchange(10), *map(rdv.exchange, range(1, 5)), *(rdv.get() for _ in range(5))))[-10:]
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
>>> task = asyncio.create_task(rdv.put(0))
>>> rdv.state_snapshot()
StateSnapshot(num_getters=0, num_putters=1, num_ops=1, idle=False)
>>> await rdv.get()
0
>>> await rdv.get('default')
'default'
>>> await task
True
>>> task = asyncio.create_task(rdv.get())
>>> await rdv.reset()
>>> task.cancelled()
True
>>> # example 2: version
>>> from .version import VersionInfo, normalize # relative imports work as if the root is asyncutils
>>> print(VersionInfo(4, 2).representation)
asyncutils v4.2.0
>>> normalize('1.2.3')
(1, 2, 3)
>>> normalize(19.0203)
(19, 2, 3)
>>> normalize(0x10F0203)
(271, 2, 3)
>>> normalize((1, 3, 5, 7))
(1, 3, 5)
>>> normalize(1.2+3.4j)
(1, 3, 0)
>>> asyncutils.autogenerate_normalizers() # get and call a function defined in the version submodule on the parent module
True
>>> normalize(Decimal('1.2345'))
(1, 23, 45)
>>> normalize(Fraction(1, 3))
(1, 3, 0)
>>> # example 3: symbols
>>> try:
...     DynamicBoundedSemaphore # because the base class of the console implementation uses exec, which requires the namespace to be an exact
...     # instance of dict, accessing most symbols as globals directly will fail
... except NameError as e: print(e)
...
name 'DynamicBoundedSemaphore' is not defined
>>> clear # special command to clear the terminal if supported; not a symbol, but an instance of the primary prompt remains on display
>>> # example 4: accessing documentation
>>> from asyncutils import find_help_url, open_help
>>> find_help_url()
'https://asyncutils.readthedocs.io/en/stable/index.html'
>>> find_help_url('TokenBucket')
'https://asyncutils.readthedocs.io/en/stable/api/asyncutils/buckets/index.html#asyncutils.buckets.TokenBucket'
>>> find_help_url('iters')
'https://asyncutils.readthedocs.io/en/stable/api/asyncutils/iters/index.html#module-asyncutils.iters'
>>> find_help_url(tools) # the "tools" submodule
'https://asyncutils.readthedocs.io/en/stable/api/asyncutils/tools/index.html#module-asyncutils.tools'
>>> find_help_url(signals.wait_for_signal)
'https://asyncutils.readthedocs.io/en/stable/api/asyncutils/signals/index.html#asyncutils.signals.wait_for_signal'
>>> find_help_url('asyncutils.event_loop')
'https://asyncutils.readthedocs.io/en/stable/api/asyncutils/base/index.html#asyncutils.base.event_loop'
>>> find_help_url(asyncutils.context.Context)
'https://asyncutils.readthedocs.io/en/stable/api/asyncutils/context/index.html#asyncutils.context.Context'
>>> find_help_url(asyncutils.channels.EventBus.audit_context)
'https://asyncutils.readthedocs.io/en/stable/api/asyncutils/channels/index.html#asyncutils.channels.EventBus.audit_context'
>>> find_help_url('CRLFProtocol.connection_lost')
'https://asyncutils.readthedocs.io/en/stable/api/asyncutils/networking/index.html#asyncutils.networking.LineProtocol.connection_lost'
>>> open_help(open_help) # Opens the https://asyncutils.readthedocs.io/en/stable/api/asyncutils/tools/index.html#asyncutils.tools.open_help\
... # page in the system default browser using the standard webbrowser library and returns success
True
>>> # example 5: context
>>> asyncutils.getcontext().update( # call the update method of the current context to modify in-place
...   {'SOCKET_TRANSPORT_LIMITS': (1024, 16384)}, # can optionally pass in a dictionary as the first and only positional argument
...   ITER_TO_AGEN_DEFAULT_USE_EXISTING_EXECUTOR=True, # fields go here; keyword arguments are accepted
...   observable_default_ntimes_n=3, # lowercase or mixed-case is allowed but not recommended
...   lEAky_BUckeT_WaiT_for_toKEnS_tick=0.1, # fields do not have to be in order
...   WAIT_FOR_SIGNAL_DEFAULT_SIGNALS=[2] # list will be automatically converted into tuple
... ) # check if a string `name` is a valid field name using `name.upper() in asyncutils.all_contextual_constants`
>>> # Due care must be exercised to avoid messing up other parts of your program relying on this context.

The following commands can all enter the console to verify the above, ordered in approximately descending order of preference. They have no known behavioural differences, and the same arguments that the asyncutils shell accepts can be appended behind each:

asyncutils # prefer for explicitness and terseness
python3 -m asyncutils # python -m on Windows; similar below
autils # shortened name for convenience
python3 asyncutils
python3 -m asyncutils.__main__
python3 asyncutils/__main__.py
# python3 -m asyncutils/__main__.py: documented to be unsupported, but works on some versions
# note: python3 asyncutils.__main__ doesn't work because python attempts to find a file called asyncutils.__main__ in the current working directory

If you’re on Python 3.13 or above and in the integrated shell of VS Code, it is recommended that you unset the PYTHON_BASIC_REPL environment variable or turn off shell integration for a better experience in my opinion, since this console does not work well with the pre-3.13 REPL at all.

Submodules

asyncutils includes a wide range of submodules tailored for specific, mostly high-level, use cases. These include asyncutils.context, asyncutils.locks, asyncutils.queues and more. A lazy loading system, complete with logging, is in place to avoid the overhead of gathering all submodules on import and make them accessible using attribute access syntax.

Note

For submodules that are not yet loaded, the value in submodules_map is an instance of an internal class with the same behaviour, except it is not inserted into sys.modules. This class is not a subclass of types.ModuleType and provides a load() method that fetches the submodule and replaces the entry in both submodules_map and sys.modules, and returns the real submodule object. For attribute accesses, it acts as a proxy to the real submodule, loading it when strictly required; however, when modifying or deleting attributes, the submodule is gotten unconditionally and replaces the proxy.

Implementation detail

The exact deferment mechanism is not part of the public API.

The remarks below are inapplicable to the contextually configured constants in context:

  • One can directly access members of submodules as attributes of the main module, which will dispatch to the appropriate submodule.

  • The submodule objects are also accessible as attributes of the library without triggering the loading immediately if not loaded.

  • Each module has an __all__ attribute, a tuple of strings representing its public API.

API Reference

This page contains auto-generated API reference documentation [1].

asyncutils

A feature-rich asynchronous utilities library with CLI and REPL support.

asyncutils.__hexversion__: Final[int]
An integer representing the current pip/conda version of this library. Comparison operators behave as expected.
For version 1.3.11, for instance, this would be 0x01030b.

Note

Equivalent to int(__version__).

asyncutils.__version__: Final[version.VersionInfo]

An instance of version.VersionInfo representing the current pip/conda version of this library.

Note

This library adheres to Semantic Versioning 2.0.0.

asyncutils.console_preloaded_submodules: Final[frozenset[_internal.prots.Submodule]]

A frozenset of submodule names which are loaded when starting the interactive console of this module.

Note

This is a strict superset of preloaded_submodules.

asyncutils.preloaded_submodules: Final[frozenset[_internal.prots.Submodule]]

A frozenset of names of submodules which are preloaded when importing the library for essential initialization.

asyncutils.submodules_map: Final[dict[_internal.prots.Submodule, types.ModuleType]]

A dict mapping submodule names to the corresponding submodule objects.

Note

For submodules that are already loaded, these are exact instances of types.ModuleType.

asyncutils.time_since_boot() ty_extensions.JustFloat

Time since the module was imported or invoked in the command line in milliseconds, as returned by time.monotonic(), as a float.

Submodules

asyncutils.__main__
Implements the console entry point for asyncutils, accessible through [python[ -m] ]asyncutils or autils.
The implementation file is executable on Unix-like systems, such that to start the console, you may technically input ./asyncutils/__main__.py in a shell of choice with asyncutils as the current working directory.

Warning

Importing asyncutils.__main__ will throw ImportError.

asyncutils._internal

For internal use of asyncutils.

Caution

All the contents of this subpackage may change without notice, unless documented in the API reference or otherwise specified.

Submodules
asyncutils._internal.helpers

Miscellaneous helper routines for asyncutils submodules that are not meant to be called by the user.

Classes

Bag

A thin dictionary subclass that supports attribute access, setting and deleting.

LoopMixinBase

The base class for LoopContextMixin.

Functions

check(→ bool)

Check if two objects are equal without calling the __eq__() method of the candidate, such that it cannot falsely claim equality.

check_methods(→ bool)

Re-implement collections.abc._check_methods().

coerce_callable(…)

Return the callable itself if the argument is callable, and return its type otherwise.

copy_and_clear(→ T)

Copy the given object, clear it, and return the copy.

create_executor(→ asyncutils.config.Executor)

Return an Executor instance for the given object, creating one if necessary, and saving it on the object as the executor attribute if save=False was not passed.

filter_out(→ types.GeneratorType[Any])

Yield items in the positional arguments not identical to the sentinel s, or None by default.

fullname(→ str)

Return the fully-qualified name of the given object, including its module, optionally removing the 'asyncutils' prefix.

get_loop_and_set(→ asyncio.AbstractEventLoop)

Return the running event loop. If there is none, create and set one first.

ismodule(→ TypeIs[types.ModuleType])

Whether the given object is a module, or an asyncutils-internal submodule object.

simple_wrap(→ T)

Return a coroutine wrapping the given awaitable. Use wrap_in_coro() instead for better error handling.

subscriptable(...)

Add a __class_getitem__() method to the given class, raising TypeError if it is already present.

Module Contents
class asyncutils._internal.helpers.Bag[T]

Bases: dict[str, T]

A thin dictionary subclass that supports attribute access, setting and deleting.

Initialize self. See help(type(self)) for accurate signature.

__delattr__(key: str, /) None

Implement delattr(self, name).

__getattr__(key: str, /) T
__setattr__(key: str, value: T, /) None

Implement setattr(self, name, value).

class asyncutils._internal.helpers.LoopMixinBase

The base class for LoopContextMixin.

make[T](aw: collections.abc.Awaitable[T], /) asyncio.Task[T]

Create a Task for the given awaitable that runs in the underlying loop.

make_fut() asyncio.Future[Any]

Create a Future attached to the underlying loop.

make_multiple[T](aws: collections.abc.Iterable[collections.abc.Awaitable[T]], /) types.GeneratorType[asyncio.Task[T]]

Return an iterator over instances of Task created for each coroutine in C, in that order.

property loop: asyncio.AbstractEventLoop

The underlying event loop.

asyncutils._internal.helpers.check(candidate: object, against: object, /) bool

Check if two objects are equal without calling the __eq__() method of the candidate, such that it cannot falsely claim equality.

asyncutils._internal.helpers.check_methods(obj: object, /, *meth: str) bool

Re-implement collections.abc._check_methods().

asyncutils._internal.helpers.coerce_callable[T: collections.abc.Callable[Ellipsis, Any]](f: T, /) T
asyncutils._internal.helpers.coerce_callable(o: T, /) type[T]

Return the callable itself if the argument is callable, and return its type otherwise.

asyncutils._internal.helpers.copy_and_clear[T: asyncutils._internal.prots.CanClearAndCopy[Any]](l: T) T

Copy the given object, clear it, and return the copy.

asyncutils._internal.helpers.create_executor(obj: object, /, save: bool = ...) asyncutils.config.Executor

Return an Executor instance for the given object, creating one if necessary, and saving it on the object as the executor attribute if save=False was not passed.

asyncutils._internal.helpers.filter_out(*a: object, s: object = ...) types.GeneratorType[Any]

Yield items in the positional arguments not identical to the sentinel s, or None by default.

asyncutils._internal.helpers.fullname(f: object, /, remove_prefix: bool = ...) str

Return the fully-qualified name of the given object, including its module, optionally removing the 'asyncutils' prefix.

asyncutils._internal.helpers.get_loop_and_set() asyncio.AbstractEventLoop

Return the running event loop. If there is none, create and set one first.

asyncutils._internal.helpers.ismodule(o: object, /) TypeIs[types.ModuleType]

Whether the given object is a module, or an asyncutils-internal submodule object.

async asyncutils._internal.helpers.simple_wrap[T](aw: collections.abc.Awaitable[T], /) T

Return a coroutine wrapping the given awaitable. Use wrap_in_coro() instead for better error handling.

asyncutils._internal.helpers.subscriptable[T](cls: type[T], /) asyncutils._internal.prots.Subscriptable[T]

Add a __class_getitem__() method to the given class, raising TypeError if it is already present.

asyncutils._internal.parsed

The submodule imported when parsing of command-line arguments is required.

Attributes

p

The argparse.ArgumentParser instance shared by asyncutils.

Module Contents
asyncutils._internal.parsed.p: Final[argparse.ArgumentParser]

The argparse.ArgumentParser instance shared by asyncutils.

asyncutils._internal.patch

Utilities to patch various things, from function signatures to annoying warnings emitted by asyncio and python itself.

Attributes

exit_sig

The signature of __exit__() and __aexit__() as a signature-patcher-compatible string. You would usually only pass this to patch_method_signatures().

Functions

patch_aio_logs(→ None)

Equivalent to logging.getLogger('asyncio').disabled = True.

patch_classmethod_signatures(→ None)

patch_function_signatures(→ None)

patch_method_signatures(→ None)

patch_unawaited_coroutine_warnings(→ None)

Silence instances of RuntimeWarning emitted when an unawaited coroutine is garbage collected.

Module Contents
asyncutils._internal.patch.patch_aio_logs() None

Equivalent to logging.getLogger('asyncio').disabled = True.

asyncutils._internal.patch.patch_classmethod_signatures(*to_patch: asyncutils._internal.prots.SigPatcherArg, follow_wrapped: bool = ...) None
patch_function_signatures(), but for class methods.
classmethod objects, though not callable, are supported.
A cls parameter (positional-only) is automatically prepended to each of the passed signatures.
asyncutils._internal.patch.patch_function_signatures(*to_patch: asyncutils._internal.prots.SigPatcherArg, follow_wrapped: bool = ...) None
Hide the original signature of functions defined in the top level of a (sub-)module with new signatures.
Each positional argument is a tuple of the form (target_func, signature), where signature looks like the portion of a function declaration within the parentheses opening to the right of the function name.
If follow_wrapped is True, the original signature is taken from the first wrapped function with a __text_signature__ attribute or the innermost function instead of the wrapper, if applicable.
Wrapped functions are found using __func__ and __wrapped__, and it is assumed in the implementation that every level only has one of these, otherwise unpredictable behaviour may arise.
Useful when, for example, dependency injection, unrepresentable sentinels, mutable defaults and other arity shenanigans are used.
asyncutils._internal.patch.patch_method_signatures(*to_patch: asyncutils._internal.prots.SigPatcherArg, follow_wrapped: bool = ...) None
patch_function_signatures(), but for instance methods.
A self parameter (positional-only) is automatically prepended to each of the passed signatures.
asyncutils._internal.patch.patch_unawaited_coroutine_warnings() None

Silence instances of RuntimeWarning emitted when an unawaited coroutine is garbage collected.

asyncutils._internal.patch.exit_sig: Final[str]

The signature of __exit__() and __aexit__() as a signature-patcher-compatible string. You would usually only pass this to patch_method_signatures().

asyncutils._internal.prots
Defines interfaces and type aliases used in this module’s stubs to facilitate lightweight type annotations, inline or otherwise.
To avoid confusion with builtin modules, this module is named prots, which may be less than descriptive, but it is what it is.
Neither this module nor any of its symbols exist at runtime.
Thus, we export nothing intentionally and prompt type checkers to emit errors when symbols here are used with from asyncutils._internal.prots import *.

Note

In the generated documentation, the instances of tyx represent the ty_extensions module. It is only available when ty is type checking the library.

Tip

For inline type annotations, wrap the imports in if TYPE_CHECKING: blocks.

Tip

Besides, run from __future__ import annotations on the top of the file for Python 3.13 or below, so that the annotations need not be quoted even prior to the implementation of PEP 563, which introduced deferred annotation evaluation.

Attributes

All

Type of the __all__ attributes of the submodules of asyncutils.

AndHashable

Most useful on duck-typed classes when specific functions require hashability.

CanCallAndHash

A hashable callable returning an awaitable.

CanExcept

The type of objects that may follow an except statement.

DualContextManager

Return type of dualcontextmanager().

EveryMethodRV

Return type of everymethod().

ExcType

The type of exc_typ in __exit__() and __aexit__() methods.

ExceptionWrapper

The return type of wrap_exc().

Executor

Type of strings representing executors that can be passed to -e/--executor.

HashAlgorithm

Names of algorithms used for calculating checksums. The default is MEMORY_MAPPED_IO_MANAGER_DEFAULT_CHECKSUM_ALG. The BLAKE2 family of algorithms, fast and somewhat secure with a low probability of collision, is the default choice.

IntCompatible

Objects accepted by the int constructor.

Middleware

Represents a middleware accepted by EventBus.

NonGroupExc

Exceptions that are not exception groups.

NotNone

The complement of None.

Observer

The type of Observable observers.

OpenFiles

The type of the open_files property of MemoryMappedIOManager.

OpenRV

The type of the return values of the open(), create() and create_sparse_file() methods of MemoryMappedIOManager.

Openable

Anything that can normally be passed to open().

Proxy

A supposed callable object having a FuncWrapper.__wrapped__ or __func__ attribute pointing to the callable it wraps.

RWLockCM

The type of the context managers returned by the reader() and writer() methods of RWLock and subclasses thereof.

Seek

Possible values of the whence parameter for MemoryMappedFile.seek(), as follows:

SigPatcherArg

The type of a positional argument passed to a signature-patching function in patch.

SpecificSubscriber

The type of subscribers for EventBus.

Submodule

Type of strings representing asyncutils submodule names.

Subscriptable

Returned by subscriptable().

SupportsIteration

Objects that support (async) iteration.

SupportsRichComparison

Objects implementing one of the operators < and >.

Timer

Type of functions that return the current time under some specification, such as time.monotonic(), time.process_time() and time.perf_counter().

ValidSlice

A slice with start, stop and step being integers or None, representing a slice that typical sequences supporting slicing should accept.

WildcardSubscriber

The type of wildcard subscribers for EventBus.

Wrapper

A function or wrapper of any depth thereof.

Exceptions

FaultyConfigA

For better type checking. Unstable.

FaultyConfigB

For better type checking. Unstable.

Classes

AUnzipConsumer

The type of each consumer in the tuple return value of aunzip().

AsyncContextManager

A protocol version of AbstractAsyncContextManager with proper overloads.

AsyncLockLike

An object that behaves like an asynchronous lock.

BenchmarkResult

The return type of benchmark().

CanClearAndCopy

An iterable that supports clearing and shallow copying.

CanWriteAndFlush

A writable and flushable 'stream', supposedly used for I/O.

CountItem

The type of items in the async generator returned by counts().

DecoratorFactoryRV

The return type of various decorator factories in func, including debounce(), throttle() and debounce().

DumpType

Encapsulates the signature of simple json-dumping functions accepted by argv_to_json() and argstr_to_json().

EventProtocol

Protocol for event objects.

EveryMethodFT

The type of functions taken by EveryMethodRV.

EveryRV

The return type of every().

FuncProxy

Same as above.

FuncWrapper

Intermediate protocol to build the recursive definition of Wrapper.

FutProtocol

The barest of protocol for future-like objects such that the class is accepted at runtime by done_fut(). Does not require the object to be awaitable, for instance.

FutWrapType

The signature of the functions accepted for the futwrap parameter in convert_to_coro_iter().

GeneratorCoroutine

Objects such as those returned by types.coroutine()-decorated generator functions.

GenericSized

A generic version of Sized.

GetAndPutProtectedQProtocol

Queues for which all mutating operations are protected by passwords. There is no requirement as to whether they are the same or different.

GetProtectedQProtocol

Queues for which get() and get_nowait() are protected by a password.

HasClassGetItem

Base class for protocol classes.

IncompleteFut

Since the type system does not allow modelling a type variable to have an upper bound parametrized by another type variable, this is necessary to type the return type of done_fut() while losing much type information.

MemoryMappedFile

The type of async memory-mapped files as opened and returned by MemoryMappedIOManager.

NoCoalesce

The type of NO_COALESCE.

NullContextType

The type of anullcontext; that is, a simple async-only version of contextlib.nullcontext() that does not depend on contextlib.

PartialInterface

PartialInterfaceMeta

Metaclass for partial interfaces, as described and justified in PartialInterface.

PathLike

An object that represents a path. Basically os.PathLike, but a Protocol.

PutProtectedQProtocol

Queues for which put() and put_nowait() are protected by a password.

QProtBase

A base protocol representing password-protected queues.

RWLockRV

The return type of the reader() and writer() methods of RWLock and subclasses thereof.

Raise

The type of RAISE.

Reader

io.Reader is not used due to version compatibility issues.

StateSnapshot

Type of snapshots of the current state of a Rendezvous object as returned by its state_snapshot() method.

StrictDualContextFactory

Protocol for the return type of the strict decorator factory overload of dualcontextmanager().

SubscriptionRV

Return type of the subscribe(), subscribe_nowait() and ntimes() methods of Observable.

SupportsCopy

An object that supports shallow copying.

SupportsGT

An object that implements the > operator.

SupportsLT

An object that implements the < operator.

SupportsMatMul

Objects that implement matrix multiplication to return an instance of its own type.

SupportsPop

Types with a pop() method.

SupportsPopLeft

Types with a popleft() method.

SupportsSlicing

Protocol for iterables with size, and index and slice access.

TaskFactory

Base class for protocol classes.

ToSyncFromLoopRV

The signature of the return value of to_sync_from_loop().

TransientBlockFromLoopRV

The signature of the return value of transient_block_from_loop().

WildcardType

Type of WILDCARD.

Writer

io.Writer is not used due to version compatibility issues.

Module Contents
exception asyncutils._internal.prots.FaultyConfigA(key: str, wrong: str, correct: tuple[str, Ellipsis], /)
exception asyncutils._internal.prots.FaultyConfigA(key: str, wrong: T, correct: R, /)

Bases: asyncutils.config.FaultyConfig

For better type checking. Unstable.

Initialize self. See help(type(self)) for accurate signature.

property correct: tuple[str, Ellipsis]
property wrong: str
exception asyncutils._internal.prots.FaultyConfigB[T, R: type | tuple[type, Ellipsis]](key: str, wrong: str, correct: tuple[str, Ellipsis], /)
exception asyncutils._internal.prots.FaultyConfigB(key: str, wrong: T, correct: R, /)

Bases: asyncutils.config.FaultyConfig

For better type checking. Unstable.

Initialize self. See help(type(self)) for accurate signature.

property correct: R
property wrong: T
class asyncutils._internal.prots.AUnzipConsumer[T]

The type of each consumer in the tuple return value of aunzip().

__aiter__() Self
async __anext__() T
close() None

Shut down the underlying queue, such that this consumer no longer receives the values at its position.

class asyncutils._internal.prots.AsyncContextManager[T]

Bases: Protocol

A protocol version of AbstractAsyncContextManager with proper overloads.

async __aenter__() T
async __aexit__(exc_typ: ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) bool | None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) bool | None
class asyncutils._internal.prots.AsyncLockLike[T]

Bases: AsyncContextManager[T], Protocol

An object that behaves like an asynchronous lock.

async acquire() bool | None
locked() bool
release() collections.abc.Awaitable[None] | None
class asyncutils._internal.prots.BenchmarkResult

Bases: NamedTuple

The return type of benchmark().

avg: float

br.avg == br.total/br.iterations.

iterations: int

The times constructor parameter.

max: float

The maximum execution time among all non-warmup calls.

min: float

The minimum execution time among all non-warmup calls.

total: float

The total execution time.

class asyncutils._internal.prots.CanClearAndCopy[T]

Bases: SupportsCopy, Protocol

An iterable that supports clearing and shallow copying.

__iter__() collections.abc.Iterator[T]
clear() None
class asyncutils._internal.prots.CanWriteAndFlush[T]

Bases: Protocol

A writable and flushable ‘stream’, supposedly used for I/O.

flush() None
write(s: T, /) int | None
class asyncutils._internal.prots.CountItem[T, R]

Bases: NamedTuple

The type of items in the async generator returned by counts().

count: int

The number of items mapping to the key up to this point, including item.

item: T

The item itself.

key: R

The key of the item, as returned by the key function.

class asyncutils._internal.prots.DecoratorFactoryRV

Bases: Protocol

The return type of various decorator factories in func, including debounce(), throttle() and debounce().

__call__[T, **P](
f: collections.abc.Callable[P, collections.abc.Awaitable[T]],
/,
) collections.abc.Callable[P, types.CoroutineType[Any, Any, T]]
class asyncutils._internal.prots.DumpType

Bases: Protocol

Encapsulates the signature of simple json-dumping functions accepted by argv_to_json() and argstr_to_json().

__call__(dct: dict[str, Any], file: io.TextIOWrapper, /) None

dict[str, Any] is used here because the callable needs only handle strict instances of dict.

class asyncutils._internal.prots.EventProtocol

Bases: Protocol

Protocol for event objects.

clear() None

Clear the event, causing future waiters to block until it is set again.

is_set() bool

Return whether the event is set.

set() None

Set the event, allowing any waiters to proceed.

async wait() Any

Asynchronously wait until the event is set.

class asyncutils._internal.prots.EveryMethodFT[T, R]

Bases: Protocol

The type of functions taken by EveryMethodRV.

__call__(self_: T, /, *a: object, **k: object) collections.abc.Awaitable[R]
class asyncutils._internal.prots.EveryRV[T]

Bases: Protocol

The return type of every().

__call__[**P](
f: collections.abc.Callable[P, collections.abc.Awaitable[T]],
/,
) collections.abc.Callable[P, types.CoroutineType[Any, Any, T | None]]
class asyncutils._internal.prots.FuncProxy[T]

Bases: Protocol

Same as above.

property __func__: T
class asyncutils._internal.prots.FuncWrapper[T]

Bases: Protocol

Intermediate protocol to build the recursive definition of Wrapper.

property __wrapped__: T
class asyncutils._internal.prots.FutProtocol[T]

Bases: Protocol

The barest of protocol for future-like objects such that the class is accepted at runtime by done_fut(). Does not require the object to be awaitable, for instance.

exception() BaseException | None

Return the exception set on the future if any.

result() T

Return the result or raise the exception set on the future.

set_exception(exc: BaseException, /) None

Set an exception on the future, causing it to be raised by any waiters.

set_result(result: T, /) None

Set a result on the future, making it available to any waiters.

class asyncutils._internal.prots.FutWrapType

Bases: Protocol

The signature of the functions accepted for the futwrap parameter in convert_to_coro_iter().

__call__[T](
future: asyncio.Future[T] | concurrent.futures.Future[T],
*,
loop: asyncio.AbstractEventLoop | None,
) asyncio.Future[T]
class asyncutils._internal.prots.GeneratorCoroutine[T, S, R]

Bases: collections.abc.Generator[T, S, R], collections.abc.Coroutine[T, S, R]

Objects such as those returned by types.coroutine()-decorated generator functions.

__await__() collections.abc.Generator[Any, None, R]
close() R | None

Raise GeneratorExit inside generator.

send(val: S, /) T

Send a value into the generator. Return next yielded value or raise StopIteration.

throw(typ: ExcType, val: object = ..., tb: types.TracebackType | None = ..., /) T
throw(exc: BaseException, val: None = ..., tb: types.TracebackType | None = ..., /) T

Raise an exception in the generator. Return next yielded value or raise StopIteration.

property __name__: str
property __qualname__: str
property gi_code: types.CodeType
property gi_frame: types.FrameType | None
property gi_running: bool
property gi_suspended: bool
property gi_yieldfrom: collections.abc.Iterator[T] | None
class asyncutils._internal.prots.GenericSized[T]

Bases: Protocol

A generic version of Sized.

__iter__() collections.abc.Iterator[T]
__len__() int
class asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, V, T]

Bases: QProtBase[R, V], Protocol

Queues for which all mutating operations are protected by passwords. There is no requirement as to whether they are the same or different.

async get(pwd: R, /) T

Remove and return an item from the password-protected queue, if the password provided was correct; raise WrongPassword otherwise. If the queue is empty, wait until an item is available.

get_nowait(pwd: R, /) T

Remove and return an item from the password-protected queue, if the password provided was correct; raise WrongPassword otherwise. If the queue is empty, raise QueueEmpty.

async put(item: T, pwd: V, /) None

Put item into the password-protected queue, if pwd is the correct password; raise WrongPassword otherwise. If the queue is full, wait until a free slot is available.

put_nowait(item: T, pwd: V, /) None

Put item into the password-protected queue, if pwd is the correct password; raise WrongPassword otherwise. If the queue is full, raise QueueFull.

class asyncutils._internal.prots.GetProtectedQProtocol[R, T]

Bases: QProtBase[R, Any], Protocol

Queues for which get() and get_nowait() are protected by a password.

async get(pwd: R, /) T

Remove and return an item from the password-protected queue, if the password provided was correct; raise WrongPassword otherwise. If the queue is empty, wait until an item is available.

get_nowait(pwd: R, /) T

Remove and return an item from the password-protected queue, if the password provided was correct; raise WrongPassword otherwise. If the queue is empty, raise QueueEmpty.

async put(item: T) None

Put item into the queue; if the queue is full, asynchronously wait until a free slot is available.

put_nowait(item: T) None

Put item into the queue immediately; raise QueueFull if impossible.

class asyncutils._internal.prots.HasClassGetItem

Bases: Protocol

Base class for protocol classes.

Protocol classes are defined as:

class Proto(Protocol):
    def meth(self) -> int:
        ...

Such classes are primarily used with static type checkers that recognize structural subtyping (static duck-typing).

For example:

class C:
    def meth(self) -> int:
        return 0

def func(x: Proto) -> int:
    return x.meth()

func(C())  # Passes static type check

See PEP 544 for details. Protocol classes decorated with @typing.runtime_checkable act as simple-minded runtime protocols that check only the presence of given attributes, ignoring their type signatures. Protocol classes can be generic, they are defined as:

class GenProto[T](Protocol):
    def meth(self) -> T:
        ...
classmethod __class_getitem__(item: TypeForm, /) types.GenericAlias
class asyncutils._internal.prots.IncompleteFut[T](*a: object, **k: object)

Bases: FutProtocol[T], PartialInterface

Since the type system does not allow modelling a type variable to have an upper bound parametrized by another type variable, this is necessary to type the return type of done_fut() while losing much type information.

class asyncutils._internal.prots.MemoryMappedFile

Bases: asyncutils.mixins.LoopContextMixin

The type of async memory-mapped files as opened and returned by MemoryMappedIOManager.

__aiter__() types.AsyncGeneratorType[bytes]

Return an asynchronous iterator over the lines of the file.

async __cleanup__() None
__iter__() collections.abc.Iterator[bytes]

Return an iterator over the lines of the file.

async __setup__() None
async aclose() None

Close the memory-mapped file and the underlying file concurrently in async. It is safe to call this method multiple times, but no other methods should be called after closing.

close() None

Close the memory-mapped file and the underlying file. It is safe to call this method multiple times, but no other methods should be called after closing.

async compact() int

Reduce the size of the file by stripping all contiguous null bytes at the end, and return the number of bytes removed.

async compare(other: Self, /, size: int = ..., offset_self: int = ..., offset_other: int = ...) bool

Compare a range of bytes in this file with a range in another file.

async copy_range(src_offset: int, dest_offset: int, size: int) bool

Copy a range of bytes from one location to another in the file.

async delete(offset: int, size: int) None

Delete a range of bytes from the file.

fileno() int

Return the file descriptor of the underlying file.

async fill(pattern: bytes, offset: int = ..., count: int = ...) None

Fill a range of the file with a repeating pattern of bytes.

find(sub: bytes, start: int | None = ..., end: int | None = ...) int

Return the lowest index in the file where the bytes sub is found, such that sub is contained in the slice file[start:end]. Return -1 if sub is not found.

async flush(offset: int = ..., size: int | None = ..., /) None

Flush the file, or a portion of it if offset and size are specified. If size is None, flush until the end of the file.

async hamming_dist(other: Self, /, size: int = ..., offset_self: int = ..., offset_other: int = ...) int

Calculate the Hamming distance in bits between a range of bytes in this file and a range in another file.

async hamming_dist_bytes(other: Self, /, size: int = ..., offset_self: int = ..., offset_other: int = ...) int

Calculate the Hamming distance in bytes between a range of bytes in this file and a range in another file.

async insert(data: bytes, offset: int) None

Insert data into the file at the specified offset.

isatty() bool

Return whether the file is connected to a TTY device.

madvise(option: int, start: int = ..., length: int | None = ...) None

Advise the kernel about how to handle the memory map by making the madvise system call.

async move(dest: int, src: int, count: int) None

Move count bytes of data within the file starting from src to dest.

async read(offset: int = ..., size: int = ...) bytes

Read size bytes from the file at offset. A negative size reads until the end of the file.

read_byte() int

Read one byte from the file at the current file pointer, advance the pointer and return the byte as an integer >=0, <256.

async read_str(offset: int = ..., size: int = ..., encoding: str = ..., errors: str = ...) str

Version of read() returning a string instead, decoded with the specified encoding and errors.

async read_until(delim: bytes, offset: int = ..., maxsize: int = ...) tuple[bytes, int]

Read bytes from the file until the delimiter is found or the maximum size is reached.

readable() Literal[True]

Return True unconditionally.

async readline(offset: int = ..., size: int | None = ..., include_newline: bool = ...) bytes

Read a line from the file at offset, up to a maximum of size bytes if size is not None, and return it, optionally including the newline character.

async readlines(hint: int = ...) list[bytes]

Read lines from the file until the total size of the lines read reaches or exceeds hint if hint is non-negative, and return a list of the lines read.

async replace(old: bytes, new: bytes, offset: int = ..., count: int = ...) int

Replace occurrences of a pattern in the file with a new pattern.

resize(new_size: int) None

Resize the file to new_size bytes. If the file is extended, the added bytes are zero-filled.

rfind(sub: bytes, start: int | None = ..., end: int | None = ...) int

Return the highest index in the file where the bytes sub is found, such that sub is contained in the slice file[start:end]. Return -1 if sub is not found.

async search(pattern: bytes, offset: int = ..., max_results: int = ...) list[int]

Return a list of the offsets of the first max_results occurrences of pattern in the file starting from offset.

search_lazy(pattern: bytes, offset: int = ...) types.AsyncGeneratorType[int]

Search for a pattern in the file starting from the specified offset, yielding the offsets of each occurrence found as they are found.

search_lazy_non_overlapping(pattern: bytes, offset: int = ...) types.AsyncGeneratorType[int]

Version of search_lazy() that ensures the offsets returned do not overlap using a greedy approach.

async search_non_overlapping(pattern: bytes, offset: int = ..., max_results: int = ...) list[int]

Version of search() that ensures the offsets returned do not overlap using a greedy approach.

async seek(pos: int, whence: Seek = ...) None

Move the file pointer to pos according to whence.

seekable() Literal[True]

Return True unconditionally.

size() int

Return the size of the file in bytes.

async smart_write(data: str, offset: int = ..., encoding: str = ..., errors: str = ...) None
async smart_write(data: bytes, offset: int = ...) None

Write data to the file at the specified offset, automatically encoding strings.

sync() None

Force the file to be written to disk, in addition to flushing the memory map.

tell() int

Return the current file pointer position.

writable() Literal[True]

Return True unconditionally.

async write(data: bytes, offset: int = ...) None

Write data into the file at offset.

write_byte(b: int, /) None

Write a byte to the file at the current file pointer and advance the pointer.

async write_str(text: str, offset: int = ..., encoding: str = ..., errors: str = ...) None

Write a string to the file at the specified offset, encoded with the specified encoding and errors.

async writelines(lines: collections.abc.Iterable[bytes], /, *, sep: bytes = ..., minimize_writes: bool = ...) None

Write each line in lines, followed by sep, into the file. If minimize_writes is True (default MEMORY_MAPPED_IO_MANAGER_DEFAULT_MINIMIZE_WRITES), write all the lines in one call.

property closed: bool

Whether the file and memory map have been closed.

property open_files: OpenFiles

A dictionary mapping tuples of the form (file, mode) to the file objects underlying this memory-mapped file.

class asyncutils._internal.prots.NoCoalesce

Bases: asyncutils.constants.SentinelBase

The type of NO_COALESCE.

__reduce__() Literal['NO_COALESCE']

Support for pickling.

class asyncutils._internal.prots.NullContextType

The type of anullcontext; that is, a simple async-only version of contextlib.nullcontext() that does not depend on contextlib.

Note

This does not support the enter_result argument of the original.

async __aenter__() None
async __aexit__(exc_typ: ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) None
class asyncutils._internal.prots.PartialInterface(*a: object, **k: object)
Base class for partial interfaces.
If it is only known that a class implements an interface, static code analysis tools might emit diagnostics on unrecognized attributes that may actually exist on the object or class.
This is a simplistic fix that asks type checkers to assume those attributes always exist and make no attempt to infer their types.
__getattr__(name: str, /) Any
class asyncutils._internal.prots.PartialInterfaceMeta

Bases: type

Metaclass for partial interfaces, as described and justified in PartialInterface.

__getattr__(name: str, /) Any
class asyncutils._internal.prots.PathLike[T]

Bases: Protocol

An object that represents a path. Basically os.PathLike, but a Protocol.

__fspath__() T
class asyncutils._internal.prots.PutProtectedQProtocol[V, T]

Bases: QProtBase[Any, V], Protocol

Queues for which put() and put_nowait() are protected by a password.

async get() T

Asynchronously get an item from the queue; if the queue is empty, wait until an item is available.

get_nowait() T

Get an item from the queue immediately; raise QueueEmpty if impossible.

async put(item: T, pwd: V, /) None

Put item into the password-protected queue, if pwd is the correct password; raise WrongPassword otherwise. If the queue is full, wait until a free slot is available.

put_nowait(item: T, pwd: V, /) None

Put item into the password-protected queue, if pwd is the correct password; raise WrongPassword otherwise. If the queue is full, raise QueueFull.

class asyncutils._internal.prots.QProtBase[R, V]

Bases: Protocol

A base protocol representing password-protected queues.

cancel_extend(msg: object = ...) bool
Cancel the currently running task to put in the initial items to the queue asynchronously, optionally with a message, which will be the argument for the CancelledError seen by the extender if any.
Return False if the task is already done or cancelled, or there was no task to begin with.
change_get_password(opw: R, npw: R) bool

Attempt to change the get password of the password-protected queue to npw given the old password opw and return success. Always returns False if the queue does not protect gets or is empty and has been shut down.

change_put_password(opw: V, npw: V) bool

Attempt to change the put password of the password-protected queue to npw given the old password opw and return success. Always returns False if the queue does not protect puts or has been shut down.

empty() bool

Check if the queue is empty.

full() bool

Check if the queue is full.

async join() None

Wait until task_done() has been called for each item put into the queue.

qsize() int

Return the number of items in the queue.

shutdown(immediate: bool = ...) None

Shut down the queue. If immediate is True, pending gets raise immediately even if the queue is not empty.

task_done() None

Mark the completion of a task gotten from the queue to join().

exc: type[asyncutils.exceptions.ForbiddenOperation]

Convenience alias for ForbiddenOperation.

property maxsize: int

Maximum number of items allowed in the queue at any moment.

class asyncutils._internal.prots.RWLockRV[T, **P]

Bases: Protocol

The return type of the reader() and writer() methods of RWLock and subclasses thereof.

__call__(*a: P, **k: P) types.CoroutineType[Any, Any, T]
reader(f: collections.abc.Callable[P, collections.abc.Awaitable[T]], /) Self

Mark another function as a reader and return an object with reader() and writer() methods.

writer(f: collections.abc.Callable[P, collections.abc.Awaitable[T]], /) Self

Mark another function as a writer and return an object with reader() and writer() methods.

class asyncutils._internal.prots.Raise

Bases: asyncutils.constants.SentinelBase

The type of RAISE.

__reduce__() Literal['RAISE']

Support for pickling.

class asyncutils._internal.prots.Reader[T]

Bases: Protocol

io.Reader is not used due to version compatibility issues.

read(size: int = ..., /) T
class asyncutils._internal.prots.StateSnapshot

Bases: NamedTuple

Type of snapshots of the current state of a Rendezvous object as returned by its state_snapshot() method.

idle: bool

ss.idle == (ss.num_getters == ss.num_putters == 0)

num_getters: int

Current number of slots waiting for values.

num_ops: int

ss.num_ops == ss.num_getters+ss.num_putters

num_putters: int

Current number of values waiting for slots.

class asyncutils._internal.prots.StrictDualContextFactory

Bases: Protocol

Protocol for the return type of the strict decorator factory overload of dualcontextmanager().

__call__[T, **P](
genf: collections.abc.Callable[P, collections.abc.Iterable[T]],
/,
) collections.abc.Callable[P, contextlib.AbstractContextManager[T]]
__call__(
agenf: collections.abc.Callable[P, collections.abc.AsyncIterable[T]],
/,
) collections.abc.Callable[P, contextlib.AbstractAsyncContextManager[T]]
class asyncutils._internal.prots.SubscriptionRV

Bases: Protocol

Return type of the subscribe(), subscribe_nowait() and ntimes() methods of Observable.

__call__(strict: bool = ...) None
class asyncutils._internal.prots.SupportsCopy

Bases: Protocol

An object that supports shallow copying.

copy() Self
class asyncutils._internal.prots.SupportsGT

Bases: Protocol

An object that implements the > operator.

__gt__(other: Self, /) bool
class asyncutils._internal.prots.SupportsLT

Bases: Protocol

An object that implements the < operator.

__lt__(other: Self, /) bool
class asyncutils._internal.prots.SupportsMatMul

Bases: Protocol

Objects that implement matrix multiplication to return an instance of its own type.

__matmul__(other: Self, /) Self
class asyncutils._internal.prots.SupportsPop[T]

Bases: Protocol

Types with a pop() method.

pop() T
class asyncutils._internal.prots.SupportsPopLeft[T]

Bases: Protocol

Types with a popleft() method.

popleft() T
class asyncutils._internal.prots.SupportsSlicing[T]

Bases: GenericSized[T], Protocol

Protocol for iterables with size, and index and slice access.

__getitem__(idx: ValidSlice, /) Self
__getitem__(idx: SupportsIndex, /) T
__len__() int
class asyncutils._internal.prots.TaskFactory[T: asyncio.Task[Any]]

Bases: Protocol

Base class for protocol classes.

Protocol classes are defined as:

class Proto(Protocol):
    def meth(self) -> int:
        ...

Such classes are primarily used with static type checkers that recognize structural subtyping (static duck-typing).

For example:

class C:
    def meth(self) -> int:
        return 0

def func(x: Proto) -> int:
    return x.meth()

func(C())  # Passes static type check

See PEP 544 for details. Protocol classes decorated with @typing.runtime_checkable act as simple-minded runtime protocols that check only the presence of given attributes, ignoring their type signatures. Protocol classes can be generic, they are defined as:

class GenProto[T](Protocol):
    def meth(self) -> T:
        ...
__call__(
loop: asyncio.AbstractEventLoop,
coro: collections.abc.Coroutine[Any, Any, Any],
*,
name: str | None = ...,
context: contextvars.Context | None = ...,
**k: object,
) T
class asyncutils._internal.prots.ToSyncFromLoopRV

Bases: Protocol

The signature of the return value of to_sync_from_loop().

__call__[R, **P](
f: collections.abc.Callable[P, collections.abc.Awaitable[R]],
/,
timeout: float | None = ...,
) collections.abc.Callable[P, R]
class asyncutils._internal.prots.TransientBlockFromLoopRV

Bases: Protocol

The signature of the return value of transient_block_from_loop().

__call__[T, **P](f: collections.abc.Callable[P, T], /, *a: P, **k: P) asyncio.Future[T]
class asyncutils._internal.prots.WildcardType

Type of WILDCARD.

__bool__() Literal[False]
class asyncutils._internal.prots.Writer[T]

Bases: Protocol

io.Writer is not used due to version compatibility issues.

write(data: T, /) int
type asyncutils._internal.prots.All = tuple[str, ...]

Type of the __all__ attributes of the submodules of asyncutils.

type asyncutils._internal.prots.AndHashable = tyx.Intersection[T, Hashable]

Most useful on duck-typed classes when specific functions require hashability.

type asyncutils._internal.prots.CanCallAndHash = AndHashable[Callable[P, Awaitable[object]]]

A hashable callable returning an awaitable.

type asyncutils._internal.prots.CanExcept = ExcType | tuple[ExcType, ...]

The type of objects that may follow an except statement.

type asyncutils._internal.prots.DualContextManager = tyx.Intersection[AbstractContextManager[T, bool], AbstractAsyncContextManager[T, bool]]

Return type of dualcontextmanager().

type asyncutils._internal.prots.EveryMethodRV = Callable[[EveryMethodFT[T, R]], Callable[Concatenate[T, ...], CoroutineType[Any, Any, R | None]]]

Return type of everymethod().

type asyncutils._internal.prots.ExcType = type[BaseException]

The type of exc_typ in __exit__() and __aexit__() methods.

asyncutils._internal.prots.ExceptionWrapper

The return type of wrap_exc().

type asyncutils._internal.prots.Executor = Literal['thread', 'process', 'interpreter', 'loky', 'loky_no_reuse', 'dask', 'ipython', 'elib_flux_cluster', 'elib_flux_job', 'elib_slurm_cluster', 'elib_slurm_job', 'elib_single_node', 'pebble_thread', 'pebble_process', 'deadpool']

Type of strings representing executors that can be passed to -e/–executor.

type asyncutils._internal.prots.HashAlgorithm = Literal['md5', 'sha1', 'sha224', 'sha256', 'sha384', 'sha512', 'blake2b', 'blake2s', 'sha3_224', 'sha3_256', 'sha3_384', 'sha3_512', 'shake_128', 'shake_256']

Names of algorithms used for calculating checksums. The default is MEMORY_MAPPED_IO_MANAGER_DEFAULT_CHECKSUM_ALG. The BLAKE2 family of algorithms, fast and somewhat secure with a low probability of collision, is the default choice.

type asyncutils._internal.prots.IntCompatible = str | SupportsInt | SupportsIndex | Buffer

Objects accepted by the int constructor.

type asyncutils._internal.prots.Middleware = Callable[[str, Any], Any]

Represents a middleware accepted by EventBus.

type asyncutils._internal.prots.NonGroupExc = tyx.Intersection[BaseException, tyx.Not[BaseExceptionGroup]]

Exceptions that are not exception groups.

type asyncutils._internal.prots.NotNone = tyx.Not[None]

The complement of None.

type asyncutils._internal.prots.Observer = Callable[Concatenate[Any, P], Awaitable[Any]]

The type of Observable observers.

type asyncutils._internal.prots.OpenFiles = dict[tuple[TextIOWrapper, Literal['r+b', 'w+b', 'x+b']], MemoryMappedFile]

The type of the open_files property of MemoryMappedIOManager.

type asyncutils._internal.prots.OpenRV = AbstractAsyncContextManager[MemoryMappedFile, None]

The type of the return values of the open(), create() and create_sparse_file() methods of MemoryMappedIOManager.

type asyncutils._internal.prots.Openable = int | str | bytes | PathLike[str] | PathLike[bytes]

Anything that can normally be passed to open().

type asyncutils._internal.prots.Proxy = FuncProxy[T] | FuncWrapper[T]

A supposed callable object having a FuncWrapper.__wrapped__ or __func__ attribute pointing to the callable it wraps.

type asyncutils._internal.prots.RWLockCM = AbstractAsyncContextManager[None, None]

The type of the context managers returned by the reader() and writer() methods of RWLock and subclasses thereof.

type asyncutils._internal.prots.Seek = Literal[0, 1, 2]

Possible values of the whence parameter for MemoryMappedFile.seek(), as follows:

type asyncutils._internal.prots.SigPatcherArg = tuple[Wrapper, str]

The type of a positional argument passed to a signature-patching function in patch.

type asyncutils._internal.prots.SpecificSubscriber = CanCallAndHash[[Any]]

The type of subscribers for EventBus.

type asyncutils._internal.prots.Submodule = Literal['altlocks', 'base', 'buckets', 'channels', 'cli', 'compete', 'config', 'console', 'constants', 'context', 'events', 'exceptions', 'func', 'futures', 'iotools', 'iterclasses', 'iters', 'locks', 'locksmiths', 'misc', 'mixins', 'networking', 'pools', 'processors', 'properties', 'queues', 'rwlocks', 'signals', 'tools', 'util', 'version']

Type of strings representing asyncutils submodule names.

type asyncutils._internal.prots.Subscriptable = type[tyx.Intersection[T, HasClassGetItem]]

Returned by subscriptable().

type asyncutils._internal.prots.SupportsIteration = Iterable[T] | AsyncIterable[T]

Objects that support (async) iteration.

type asyncutils._internal.prots.SupportsRichComparison = SupportsLT | SupportsGT

Objects implementing one of the operators < and >.

type asyncutils._internal.prots.Timer = Callable[[], float]

Type of functions that return the current time under some specification, such as time.monotonic(), time.process_time() and time.perf_counter().

type asyncutils._internal.prots.ValidSlice = slice[SupportsIndex | None, SupportsIndex | None, SupportsIndex | None]

A slice with start, stop and step being integers or None, representing a slice that typical sequences supporting slicing should accept.

type asyncutils._internal.prots.WildcardSubscriber = CanCallAndHash[[str, Any]]

The type of wildcard subscribers for EventBus.

type asyncutils._internal.prots.Wrapper = FunctionType | Proxy[FunctionType | Wrapper]

A function or wrapper of any depth thereof.

asyncutils._internal.unparsed

Automatically read the config from the file whose path is specified by AUTILSCFGPATH.

Important

Values will be overwritten by command-line arguments when this module runs as a script.

Attributes

C

The contextual portion of the configuration as a flattened dict mapping upper-case keys to values.

N

The frozen part of the configuration as a light namespace-like object.

Z

A dict mapping file extensions to module names for loading config files. Is queried by loadf().

c

The path to the config file used, or an empty string if no config file was read.

Functions

r(…)

Load a config file from the given string path or file descriptor (in which case the file extension should be passed but leniently defaults to json), from which the file extension and thus appropriate parsing library is determined.

Module Contents
asyncutils._internal.unparsed.r(path: int, ext: str, /) dict[str, Any]
asyncutils._internal.unparsed.r(path: str, ext: str | None = ..., /) dict[str, Any]

Load a config file from the given string path or file descriptor (in which case the file extension should be passed but leniently defaults to json), from which the file extension and thus appropriate parsing library is determined.

asyncutils._internal.unparsed.C: Final[dict[str, Any]]

The contextual portion of the configuration as a flattened dict mapping upper-case keys to values.

asyncutils._internal.unparsed.N: Final[asyncutils._internal.helpers.Bag[Any]]

The frozen part of the configuration as a light namespace-like object.

asyncutils._internal.unparsed.Z: Final[dict[str, str]]

A dict mapping file extensions to module names for loading config files. Is queried by loadf().

asyncutils._internal.unparsed.c: Final[str]

The path to the config file used, or an empty string if no config file was read.

asyncutils.altlocks

Non-conventional asynchronous synchronization primitives that may not adhere to the traditional lock interface.

Classes

CircuitBreaker

DynamicThrottle

Limit the rate of a function being called.

Releasing

Essentially invert the roles of the async enter and exit methods of a lock.

ResourceGuard

A sync- and async-compatible context manager, inspired by anyio.ResourceGuard, which causes contention of a shared resource to fail fast.

StatefulBarrier

An async barrier, that unlike traditional barriers, accumulates state from parties in a deque and makes it available once the barrier is tripped.

UniqueResourceGuard

A subclass of ResourceGuard that only allows one guard per object. Cannot be further subclassed.

Module Contents
class asyncutils.altlocks.CircuitBreaker
The circuit breaker pattern. Use on async functions that may fail often, such as requests to an unreliable server.
Instances can be used as decorators, unless instantiated with a function as the first parameter, in which case the decorated function is returned.
Construct a circuit breaker, whose circuit is initially closed.
If name is passed, use it as its name; return a function wrapping f otherwise, deriving the name of the circuit breaker from the function. This derivation follows exactly one level of __wrapped__-based wrapping after retrieving the __func__ attribute if present.
Pass exceptions that are expected to happen through the exc parameter.
When the decorated function fails more than max_fails times (default CIRCUIT_BREAKER_DEFAULT_MAX_FAILS), the breaker triggers (opens the circuit, so to say) and disallows further calls of the wrapped functions by throwing an exception.
This state persists until the reset timeout expires (default CIRCUIT_BREAKER_DEFAULT_RESET). Then, the breaker enters the half-open state.
If the function completes successfully when the breaker is half-open under max_half_open_calls (default CIRCUIT_BREAKER_DEFAULT_MAX_HALF_OPEN_CALLS) tries, the circuit closes automatically. Otherwise, the circuit reopens.
class State

Bases: enum.IntEnum

Enum where members are also (and must be) ints

Initialize self. See help(type(self)) for accurate signature.

CLOSED = 0

The closed state.

HALF_OPEN = 1

The half-open state.

OPEN = 2

The open state.

__call__[T, **P](
f: collections.abc.Callable[P, collections.abc.Awaitable[T]],
/,
*,
timer: asyncutils._internal.prots.Timer = ...,
default: T = ...,
) collections.abc.Callable[P, types.CoroutineType[Any, Any, T]]
Apply the circuit breaker to a function f returning an awaitable, and return a wrapper function with the same signature that strictly returns coroutines.
timer (default time.monotonic()) is used to get the current time to calculate the timeout.
If passed, default is returned if an expected exception is raised, also suppressing that exception.

Caution

Care should be taken when applying the same circuit breaker to multiple functions, as the calls counters will be shared.

property fails: int

Current count of consecutive failures.

property name: str

The name of the circuit breaker, to be shown in error messages.

property state: State

The current state of the circuit breaker.

class asyncutils.altlocks.DynamicThrottle(
init_rate: float,
min_rate: float = ...,
max_rate: float = ...,
window: int | None = ...,
*,
ubound: float | None = ...,
lbound: float | None = ...,
ufactor: float | None = ...,
lfactor: float | None = ...,
jitter: float | None = ...,
timer: asyncutils._internal.prots.Timer = ...,
rand: collections.abc.Callable[[float], float] = ...,
)

Limit the rate of a function being called.

See also

RateLimited

AdvancedRateLimit

Classes that serve similar rate-limiting functionality.

async __aenter__() None

Wait for the time as computed by the throttler, with some jitter applied, to pass, such that the rate is maintained.

async __aexit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

If an error caused the context manager, increment fails and re-raise; otherwise, increment successes. Also adjust the rate if necessary.

reset() None

Reset the counts of successes and fails.

property ctime: ty_extensions.JustFloat

The current time as returned by timer.

property fails: int

Current number of failed calls. Reset periodically.

property jitter: float

The current jitter in calculating the wait time.

property rate: float

The current rate.

property successes: int

Current number of succeeded calls; reset periodically.

class asyncutils.altlocks.Releasing(lock: asyncutils._internal.prots.AsyncLockLike[object], /)

Essentially invert the roles of the async enter and exit methods of a lock.

Instantiate the async context manager to release lock on entry and re-acquires it on exit.

async __aenter__() None

Call the release method of the lock, awaiting if it returns a coroutine.

async __aexit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Re-enter the lock, propagating errors.

class asyncutils.altlocks.ResourceGuard[T]

Bases: asyncutils.mixins.AsyncContextMixin[None]

A sync- and async-compatible context manager, inspired by anyio.ResourceGuard, which causes contention of a shared resource to fail fast.

Tip

A strong reference to the object will be held for the lifetime of the guard.

Note

The guard is not held upon creation.

action is used in error messages to describe the action being attempted on the resource, such as 'access' or 'close'.
rsrc is used in error messages to describe the resource by calling its __repr__(); if not passed, an index is automatically assigned to the resource.
__enter__() None
Throw ResourceBusy if the resource is already being guarded.
Otherwise, mark the resource as guarded, such that guarded evaluates to True.
__exit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
__exit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Mark the resource as no longer guarded.

yields_resource() asyncutils._internal.prots.DualContextManager[T]

Return a one-off context manager serving the same purpose as the guard but giving the resource on entry.

property action: str

The action being attempted on the resource, as passed to the constructor. Should be a gerund.

property guarded: bool

Whether the resource is currently being guarded.

property success_ratio: float

The current ratio of successful acquisitions to total acquisition attempts, or 0.0 if there have been no attempts.

class asyncutils.altlocks.StatefulBarrier[T](parties: int, name: str = ..., *, max_state: int | None = ...)
class asyncutils.altlocks.StatefulBarrier(
parties: int,
*,
init_state: asyncutils._internal.prots.SupportsIteration[T],
max_state: int | None = ...,
)
class asyncutils.altlocks.StatefulBarrier(
parties: int,
name: str,
init_state: asyncutils._internal.prots.SupportsIteration[T],
max_state: int | None = ...,
)

Bases: asyncutils.mixins.AwaitableMixin[tuple[int, collections.deque[T]]]

An async barrier, that unlike traditional barriers, accumulates state from parties in a deque and makes it available once the barrier is tripped.

  • parties (required): The number of parties required to break the barrier.

  • name: The name of the barrier, to appear in error messages.

  • init_state: An iterable storing the initial state. The iterable will be exhausted eventually.

  • max_state: Maximum length of state to store. Older state will be expelled.

async abort() None

Abort the barrier, signalling BrokenBarrierError to present waiting parties.

raise_for_abort() None

Throw BrokenBarrierError if the barrier has been aborted.

async wait(state: T = ..., timeout: float | None = ...) tuple[int, collections.deque[T]]
Note that the calling party is waiting for the barrier, optionally adding some state.
If the barrier has already been aborted or broken, raise BrokenBarrierError.
Once enough parties are waiting, all callers receive a tuple (pos, states), where states is the deque of stored state and pos the number of parties having arrived before this one.
property broken: bool

Whether the barrier is broken.

property n_waiting: int

Number of parties currently waiting.

property parties: int

Total number of parties, arrived or not.

property remaining_parties: int

Number of parties the waiting parties are waiting for.

class asyncutils.altlocks.UniqueResourceGuard[T: collections.abc.Hashable]

Bases: ResourceGuard[T]

A subclass of ResourceGuard that only allows one guard per object. Cannot be further subclassed.

Note

You must keep the guard alive for as long as you want the resource to be guarded.

Caution

This class does not stop the object from having an instance of ResourceGuard (or subclass thereof) from guarding it simultaneously.

Implementation detail

Instances are weakly referenceable.

If the object already has a guard, return that guard, regardless of whether it is held. In that case, the action parameter is ignored and a warning is issued.
Otherwise, create and return a new guard for the object, using the action parameter in error messages.

Attention

The error will be seen by the user only when they actually try to acquire the guard if it is already held.

classmethod clear_cache() None

Clear the internal cache mapping guarded objects to their guards. Call only when you are sure no guards are in use.

asyncutils.base

The most useful and fundamental patterns and helpers core to this module and are therefore required by asyncutils.console, among many other submodules.

Attributes

dummy_task

An awaitable object that completes immediately. Also an exhausted generator.

yield_to_event_loop

An awaitable and picklable singleton that yields control to the event loop for exactly one iteration when awaited, much like asyncio.sleep(s) for non-positive s.

Classes

event_loop

A context manager controlling lifecycles of native event loops. Has specialized handling for asyncio implementation details.

Functions

adisembowel(→ types.AsyncGeneratorType[T])

Asynchronously disembowel an iterable from the right using its pop method and yield its items from right to left.

adisembowel_left(→ types.AsyncGeneratorType[T])

Asynchronously disembowel an iterable from the left using its popleft method and yield its items from left to right.

aenumerate(→ types.AsyncGeneratorType[tuple[int, T]])

Async version of enumerate, except it is not a class and additionally supports the step parameter.

aiter_to_gen(…)

collect(→ list[T])

collect_into(→ None)

drop(→ types.AsyncGeneratorType[T])

Discard n items from the (async) iterable and yield the rest. If there are not enough items and raising is True, throw ItemsExhausted.

iter_to_agen(…)

safe_cancel_batch(…)

sleep_forever(→ NoReturn)

Return a coroutine that only completes when an exception is thrown in. The exception is propagated.

take(…)

Module Contents
class asyncutils.base.event_loop

A context manager controlling lifecycles of native event loops. Has specialized handling for asyncio implementation details.

Construct a new event loop manager. Arguments are self-explanatory. Pass as appropriate; all are applied on top of EVENT_LOOP_BASE_FLAGS.

class Flags

Bases: enum.IntFlag

An enumeration of all keyword arguments accepted by the constructor in order of the offset corresponding to the flag in the flags representation.

Initialize self. See help(type(self)) for accurate signature.

ATTEMPT_AENTER = 8192
CANCEL_ALL_TASKS = 64
CLOSE_EXISTING_ON_EXIT = 8
DISALLOW_REUSE = 1024
FAIL_SILENT = 512
FLIP_RELEASE_LOOP_ON_FINALIZATION = 1
KEEP_CREATED_OPEN_ON_EXIT = 32
KEEP_LOOP = 128
NEVER_CLEAR_TASKS_ON_REUSE = 4
NEVER_ENTER = 4096
NO_REUSE = 2048
SILENT_ON_FINALIZE = 2
SOMETIMES_CONTINUE_ON_EXIT = 16
SUPPRESS_INNER_AEXIT_ON_RUNTIME_ERROR = 32768
SUPPRESS_INNER_EXIT_ON_RUNTIME_ERROR = 16384
SUPPRESS_RUNTIME_ERRORS = 256
class State

Bases: enum.IntFlag

Flags representing the possible states of the manager.

Initialize self. See help(type(self)) for accurate signature.

AENTERED_INNER = 8
CREATED_LOOP = 2
ENTERED = 1
ENTERED_INNER = 4
__contains__(flag_name: str, /) bool
__contains__(flag: int, /) bool

Return whether the manager has the flag specified by name or flag.

__del__() None

Finalize the manager by calling __exit__() if necessary.

__enter__() asyncio.AbstractEventLoop

Enter the context, returning the underlying asyncio event loop, which is fetched on demand.

__exit__(exc_typ: None, exc_val: None, exc_tb: None, /) Literal[False]
__exit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) bool

Exit the context. This stops and closes the event loop if the flags say so.

__hash__() int

Return the flags of the manager as its hash, not considering its state.

__reduce__() tuple[collections.abc.Callable[[int], Self], tuple[int]]

Support for pickling.

_get_unclosed_loop(factory: collections.abc.Callable[[], asyncio.AbstractEventLoop] = ...) asyncio.AbstractEventLoop

Return a usable asyncio event loop from the internal pool, or a new event loop if there are none.

clear_flags(mask_to_keep: int = ...) None

Reset the configuration of the manager to the equivalent of passing all keyword arguments as False, except those covered by mask_to_keep.

copy_flags() Self

Return an unentered instance with the same configuration as this that manages a different event loop.

factory_reset() None

Restore the default settings from the context (i.e., set the flags to EVENT_LOOP_BASE_FLAGS).

flags_eq(other: Self, /) bool
flags_eq(flags: int, /) bool

Return whether the configuration of this manager is the same as that of other, regardless of their respective states.

classmethod from_flags(flags: int, /) Self

Construct an instance from flags, a bitwise or of options (default EVENT_LOOP_BASE_FLAGS).

asyncutils.base.adisembowel[T](it: asyncutils._internal.prots.SupportsPop[T], /) types.AsyncGeneratorType[T]

Asynchronously disembowel an iterable from the right using its pop method and yield its items from right to left.

asyncutils.base.adisembowel_left[T](it: asyncutils._internal.prots.SupportsPopLeft[T], /) types.AsyncGeneratorType[T]

Asynchronously disembowel an iterable from the left using its popleft method and yield its items from left to right.

asyncutils.base.aenumerate[T](
it: asyncutils._internal.prots.SupportsIteration[T],
start: int = ...,
step: int = ...,
) types.AsyncGeneratorType[tuple[int, T]]

Async version of enumerate, except it is not a class and additionally supports the step parameter.

asyncutils.base.aiter_to_gen[T, R](
ait: collections.abc.AsyncGenerator[T, R],
*,
use_futures: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
strict: bool = ...,
) types.GeneratorType[T, R]
asyncutils.base.aiter_to_gen(
ait: collections.abc.AsyncIterable[T],
*,
use_futures: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
strict: bool = ...,
) types.GeneratorType[T]
asyncutils.base.aiter_to_gen(
ait: collections.abc.Generator[T, R, V],
*,
use_futures: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
strict: Literal[False] = ...,
) types.GeneratorType[T, R, V]
asyncutils.base.aiter_to_gen(
ait: collections.abc.Iterable[T],
*,
use_futures: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
strict: Literal[False] = ...,
) types.GeneratorType[T]
Convert an async iterable ait to a sync generator.
If the event loop is currently running and use_futures is False (default AITER_TO_GEN_DEFAULT_ALLOW_FUTURES), raise RuntimeError to clarify that concurrent.futures.Future must be used in this case, one per item yielded, which is somewhat inefficient, but that can’t be helped.
If strict is True (default AITER_TO_GEN_DEFAULT_STRICT), only async iterables are accepted.
async asyncutils.base.collect[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int | None = ...,
default: T | asyncutils._internal.prots.Raise = ...,
) list[T]
Return a list of the first n items in the (async) iterable, consuming it up to that point exactly.
If there are less than n items to collect, throw ItemsExhausted if default is RAISE and emit a debug message through the logger before padding the behind of the list with copies of the default if passed otherwise.

See also

basic_collect()

a possibly slightly faster variant that doesn’t accept a default.

to_list()

the most bare-bones variant equivalent to the case when n is not passed.

async asyncutils.base.collect_into[T](
out: collections.abc.MutableSequence[T],
it: asyncutils._internal.prots.SupportsIteration[T],
n: int | None = ...,
default: T | asyncutils._internal.prots.Raise = ...,
) None
Extend a mutable sequence with the first n items in the (async) iterable, consuming it up to that point exactly.
If there are less than n items to collect, throw ItemsExhausted if default is RAISE and emit a debug message through the logger before padding the behind of the list with copies of the default if passed otherwise.
asyncutils.base.drop[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int,
*,
raising: bool = ...,
) types.AsyncGeneratorType[T]

Discard n items from the (async) iterable and yield the rest. If there are not enough items and raising is True, throw ItemsExhausted.

asyncutils.base.iter_to_agen[T, R](
it: collections.abc.AsyncGenerator[T, R],
sentinel: T = ...,
*,
use_existing_executor: bool = ...,
create_executor: bool = ...,
strict: Literal[False] = ...,
) types.AsyncGeneratorType[T, R]
asyncutils.base.iter_to_agen(
it: collections.abc.AsyncIterable[T],
sentinel: T = ...,
*,
use_existing_executor: bool = ...,
create_executor: bool = ...,
strict: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.base.iter_to_agen(
it: collections.abc.Iterable[T],
*,
use_existing_executor: bool = ...,
create_executor: bool = ...,
strict: bool = ...,
) types.AsyncGeneratorType[T]
asyncutils.base.iter_to_agen(
it: collections.abc.Iterable[T],
sentinel: T,
*,
use_existing_executor: bool = ...,
create_executor: bool = ...,
strict: bool = ...,
) types.AsyncGeneratorType[T]
Convert the (async) iterable it to an async generator, blocking as little as possible.
If it is an async generator and sentinel is not passed, it is returned as is.
Values sent to the return async generator will be passed through to the original.
The async generator will stop when it encounters an item identical to sentinel.
When use_existing_executor=True is passed (default ITER_TO_AGEN_DEFAULT_USE_EXISTING_EXECUTOR), the function will attempt to use an existing executor as created by previous calls specifying create_executor=True (default ITER_TO_AGEN_DEFAULT_MAY_CREATE_EXECUTOR) to advance the iterable, and fall back to blocking the event loop every step without an executor.
If strict is True (default ITER_TO_AGEN_DEFAULT_STRICT), only sync iterables are accepted.
async asyncutils.base.safe_cancel_batch[T](
batch: asyncutils._internal.prots.SupportsIteration[asyncio.Future[T]],
/,
*,
callback: collections.abc.Callable[[T | BaseException], object] | None = ...,
disembowel: Literal[False] = ...,
raising: bool = ...,
) None
async asyncutils.base.safe_cancel_batch(
batch: asyncutils._internal.prots.SupportsPop[asyncio.Future[T]],
/,
*,
callback: collections.abc.Callable[[T | BaseException], object] | None = ...,
disembowel: Literal[True],
raising: bool = ...,
) None
Cancel an (async) iterable of futures, waiting for the cancellations to complete asynchronously.
The batch cancellation itself can be cancelled, but less reliably and granularly than safe_cancel().
Afterwards, if disembowel is True, clear the iterable using its pop() method repeatedly, falling back to clear().
The callback is called on each result or exception of the futures after CancelledError was thrown into them concurrently.
If raising is True, all calls of the callback that themselves threw exceptions are collected into a BaseExceptionGroup, which is then raised.
async asyncutils.base.sleep_forever() NoReturn

Return a coroutine that only completes when an exception is thrown in. The exception is propagated.

asyncutils.base.take[T](it: asyncutils._internal.prots.SupportsIteration[T], n: None, default: T = ...) types.AsyncGeneratorType[T]
asyncutils.base.take(
it: asyncutils._internal.prots.SupportsIteration[T],
n: int,
default: T | asyncutils._internal.prots.Raise = ...,
) types.AsyncGeneratorType[T]
Yield n items from the (async) iterable. If default is RAISE, throw ItemsExhausted if there are less than n items to take.
Otherwise, pad the behind of the async generator with the default until there are exactly n items if it was passed.
If n is None, yield all items, then yield default indefinitely if passed.
asyncutils.base.dummy_task: asyncutils._internal.prots.GeneratorCoroutine[Never, Any, Any]

An awaitable object that completes immediately. Also an exhausted generator.

Implementation detail

This is achieved by setting the inspect.CO_ITERABLE_COROUTINE flag on the code of a generator function.

asyncutils.base.yield_to_event_loop: collections.abc.Awaitable[None]

An awaitable and picklable singleton that yields control to the event loop for exactly one iteration when awaited, much like asyncio.sleep(s) for non-positive s.

asyncutils.buckets
Classes
Module Contents
class asyncutils.buckets.LeakyBucket(
capacity: float,
leak: float,
min_factor: float = ...,
max_factor: float = ...,
external_factor_settable: bool = ...,
timer: asyncutils._internal.prots.Timer = ...,
)

Bases: asyncutils.mixins.AsyncContextMixin[LeakyBucket], asyncutils._internal.helpers.LoopMixinBase

A leaky bucket rate limiter with adaptive flow control. Use as a context manager.
In the context, tokens leak from the bucket at a constant rate. Operations can add tokens to the bucket.
The bucket includes an adaptive factor that adjusts based on current fill level to provide smoother rate limiting under varying loads, as dictated by LEAKY_BUCKET_ADJMAP, a sequence of tuples (min_capacity, (lbound, lfactor, ubound, ufactor)) monotonically descending in min_capacity.
__exit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
__exit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Stop draining the tokens in the bucket.

async acquire(amount: float = ...) bool

Attempt to add amount tokens to the bucket immediately (default LEAKY_BUCKET_DEFAULT_ACQUIRE_TOKENS); return success.

async wait_for_tokens(amount: float = ...) ty_extensions.JustFloat

Keep asynchronously sleeping, with a maximum interval of LEAKY_BUCKET_WAIT_FOR_TOKENS_TICK each time, until amount tokens can be added to the bucket at once (default LEAKY_BUCKET_DEFAULT_WAIT_FOR_TOKENS_TOKENS), and do so, returning the total wait time.

Note

The sleep interval is calculated based on the amount of tokens requested, the current number of tokens, the bucket capacity, the leaking rate and the current factor.

property factor: float

The current adaptive factor.

class asyncutils.buckets.TokenBucket(rate: float, capacity: float, timer: asyncutils._internal.prots.Timer = ...)
A token bucket rate limiter that controls the rate of operations.
The bucket fills up with tokens at a fixed rate, with each operation consuming a certain amount of tokens.
If there are not enough tokens, the operation must wait until there are.
  • rate: The number of tokens the bucket gains per time interval as a float, as defined by the timer.

  • capacity: The maximum number of tokens the bucket can hold as a float.

  • timer (optional): A function such as time.time() that returns the current time; default monotonic().

async consume(tokens: float = ...) None

Consume tokens from the bucket as described. The default amount to consume if tokens is not passed can be set through TOKEN_BUCKET_DEFAULT_CONSUME_TOKENS.

property capacity: float

The capacity of the bucket.

asyncutils.channels

Bridges between asynchronous consumers/subscribers and producers/publishers.

Classes

EventBus

Observable

A class representing an observable stream of data, that observers can subscribe to and receive notifications from.

Rendezvous

A rendezvous object, emulating Golang's unbuffered channels.

Module Contents
class asyncutils.channels.EventBus(
name: str = ...,
*,
handler: collections.abc.Callable[[BaseException], None] = ...,
max_concurrent: int = ...,
tracking_stats: bool = ...,
)

Bases: asyncutils.mixins.LoopContextMixin

A class abstracting the communication between notable events and asynchronous callbacks (an async auditing system), that can optionally be hooked up to sys.audit.
Has extensive telemetry and middleware support, allowing data to be processed in a pipeline and eventually passed to subscribers. Subscribers must be hashable!
A subscriber is a function that will be called every time data is published, with the corresponding data passed in. Publishing is thus the action of triggering these subscribers.
Wildcard subscribers should take the event type as the first argument, and the event data as the next; while specific subscribers should take the event data as the only argument.

Caution

Use instances as context managers only for proper setup and shutdown.

All the arguments below are optional.

  • name: The name of this event bus, which will appear in error messages.

  • handler: A function that takes an exception having occurred in a subscribers and handles it.

  • max_concurrent: The maximum number of concurrent callbacks; default EVENT_BUS_DEFAULT_MAX_CONCURRENT.

  • tracking_stats: Whether to remember the amount of published data to subscribers of each event type.

async __cleanup__() None
async __setup__() None
add_middleware(middleware: asyncutils._internal.prots.Middleware) int
Append a middleware to the back of the pipe of middlewares, and return a permanent cookie that can be passed to remove_middleware() to invalidate it. O(1) time.
The middleware must take the event type as the first argument and the associated data as the second.
If the middleware does not recognize the event type, it should simply return the data immediately.
There is no protection in place against malicious middlewares but the user’s abstraction.
It is preferred that the middleware be a coroutine function.
Each middleware should be extremely optimized, such as through C extensions, to avoid hindrance of the publishing.
When publishing occurs, the first middleware takes the initial data, does some processing asynchronously, and passes the modified data to the second middleware, and so forth. Insertion order is maintained. This may be different from the typical meaning of a ‘middleware’.
The output of the final middleware is broadcast to each subscriber concurrently. Subscribers cannot see the initial data.
add_temp_middleware(middleware: asyncutils._internal.prots.Middleware, until: asyncio.Future[Any]) None

Add a middleware that should take effect until the future until is done, after which the result of the future will be treated as the result of the middleware on removal. No cookie is returned in this case.

audit_context() asyncutils._internal.prots.DualContextManager[None]

Start receiving publications from and sending publications to sys.audit() upon entry and stop on exit. Use as a context manager.

auditor(event: str, args: tuple[object, Ellipsis], /) None
The auditor of the event bus. You probably don’t want to call this directly.
Not an instance method at runtime, just a function as an attribute of the instance.
clear(event_type: str) weakref.WeakSet[asyncutils._internal.prots.SpecificSubscriber] | None
clear(
event_type: asyncutils._internal.prots.WildcardType,
) weakref.WeakSet[asyncutils._internal.prots.WildcardSubscriber] | None
clear() None

Remove all subscribers for the event type and return them. If not passed, clear all subscribers but persist statistics unlike clear_all().

clear_all() None

Remove all subscribers and clear statistics.

clear_stats() None

Clear the event publication statistics.

clear_wildcards() weakref.WeakSet[asyncutils._internal.prots.WildcardSubscriber] | None

Equivalent to bus.clear(EventBus.WILDCARD).

event_stream(
event_type: str,
*,
timeout: float | None = ...,
item_timeout: float | None = ...,
bufsize: int = ...,
) types.AsyncGeneratorType[Any]
event_stream(
*,
timeout: float | None = ...,
item_timeout: float | None = ...,
bufsize: int = ...,
) types.AsyncGeneratorType[tuple[str, Any]]
Open an event stream for the specified event type, that is, an async generator from which consumers can receive events and the corresponding data as they occur.
If event_type is not passed, the stream will include the event type in the output.
events() set[str]

Return a set of the names of the current event types.

async feed_event(data: object, /, *, timeout: float | None = ...) None
async feed_event(event_type: str, data: object, /, *, timeout: float | None = ...) None

Feed the data for an event into the event stream, the queue for which is created if necessary, such that the event stream needs not be active.

get_event_stats() collections.defaultdict[str, int]

Return a copy of the stats, mapping event type to number of published events.

async handle_exception(e: BaseException) None

Asynchronously handle an exception according to the handler initialization parameter, which can be a sync or async function.

has_subscribers(event_type: str | asyncutils._internal.prots.WildcardType) bool

Whether the event type has any subscribers.

is_auditing() bool

Whether the event bus is connected to sys.audit().

is_subscribed(subscriber: asyncutils._internal.prots.SpecificSubscriber, event_type: str = ...) bool
is_subscribed(
subscriber: asyncutils._internal.prots.WildcardSubscriber,
event_type: asyncutils._internal.prots.WildcardType = ...,
) bool

Whether the callback is subscribed for the event type, or subscribed for any event type if event_type is not passed.

on[T: asyncutils._internal.prots.SpecificSubscriber](event_type: str) collections.abc.Callable[[T], T]
on(event_type: asyncutils._internal.prots.WildcardType) collections.abc.Callable[[T], T]

Return a decorator for functions to subscribe to this event bus under the specified event type.

async publish(
event_type: str,
data: object = ...,
*,
wait: bool = ...,
safe: bool = ...,
timeout: float | None = ...,
chaperone: collections.abc.Callable[[ExceptionGroup | Exception], object] | None = ...,
) None
Publish an event, that is, some data attached to an event type, to the subscribers involved, with timeout timeout.
Each subscriber for that event type and wildcard subscribers will be triggered by the publication, receiving the data after processing by the middlewares in order.
If wait is False (default True), possibly return before the publication completes.
If safe is False (default True), drop error handling logic in callback execution.
chaperone, if passed, should be a function processing non-severe exceptions (instances of Exception and ExceptionGroup) in the callbacks.
Otherwise, these exception( group)s are flattened and collected into an ExceptionGroup and propagated; the caller should be prepared to handle that case.
raise_for_shutdown() None

Throw an exception if the event bus is shutting down.

remove_middleware[T](cookie: int, *, result: T, strict: bool = ...) T
remove_middleware(cookie: int, *, result: object = ..., strict: bool = ...) Any
Remove a previously added middleware, via add_middleware() or add_temp_middleware(), and return its result. O(1) time.
If strict is True and the middleware was never added, throw ValueError.
If the middleware has an associated future add_temp_middleware() and it is done, return its result. If an exception was set, propagate it.
Otherwise, set its result to result and return it.
async shutdown(immediate: bool = ..., *, timeout: float | None = ..., preserve_stats: bool = ...) None
Gracefully shut down the event bus.
After the shutdown, publications fail fast and middlewares are cleared.
This waits for as many subscriber callbacks to complete as possible, within timeout seconds if specified.
If immediate is True, getters for the queue for the event stream will error immediately.
If preserve_stats is True, the event publication statistics will be saved and accessible with get_event_stats().
start_audit() None

Connect the audit hook of the bus to sys.audit(), creating if necessary. Incurs overhead. Use with caution.

start_tracking() None

Start tracking event publication statistics (number of publications under each event type).

stop_audit() None

Disconnect the audit hook of the bus from sys.audit(). Note that it is currently impossible to actually remove an audit hook, so this function just deactivates it.

stop_tracking(ret_stats: Literal[False] = ...) None
stop_tracking(ret_stats: Literal[True]) collections.defaultdict[str, int]

Stop tracking event publication statistics. If ret_stats is True, return a dictionary of the stats up to that point, with keys corresponding to event types and values the number of publications.

subscribe[T: asyncutils._internal.prots.SpecificSubscriber](subscriber: T, /, event_type: str) T
subscribe(subscriber: T, /, event_type: asyncutils._internal.prots.WildcardType = ...) T

Add a subscriber to the event bus under the specified event type (if unspecified, add as wildcard). Return the subscriber to allow usage as a decorator.

async subscribe_until[T](
fut: asyncio.Future[T],
subscriber: asyncutils._internal.prots.SpecificSubscriber,
event_type: str,
*,
till_permanent: float | None = ...,
) asyncio.Task[T]
async subscribe_until(
fut: asyncio.Future[T],
subscriber: asyncutils._internal.prots.WildcardSubscriber,
event_type: asyncutils._internal.prots.WildcardType = ...,
*,
till_permanent: float | None = ...,
) asyncio.Task[T]
Add the subscriber under the event type (as a wildcard if event_type is WILDCARD or not passed) and return a task.
The subscriber is removed once fut completes, and its result returned through the returned task.
After till_permanent seconds elapse (if passed), the task errors and the subscriber is left under that event type.
subscriber_count(event_type: str | asyncutils._internal.prots.WildcardType) int

Return the number of subscribers to event_type.

subscribers_for(event_type: str) weakref.WeakSet[asyncutils._internal.prots.SpecificSubscriber]
subscribers_for(
event_type: asyncutils._internal.prots.WildcardType,
) weakref.WeakSet[asyncutils._internal.prots.WildcardSubscriber]

Return a weakref.WeakSet of subscribers for the event type.

sync_start_publish(
event_type: str,
data: object = ...,
*,
safe: bool = ...,
timeout: float | None = ...,
chaperone: collections.abc.Callable[[ExceptionGroup | Exception], object] | None = ...,
) None

Begin a publication synchronously. Parameters are as in publish(), below.

tracking_context(
stats_receiver: asyncio.Future[collections.abc.Mapping[str, int]] | None = ...,
) asyncutils._internal.prots.DualContextManager[None]

Context manager, under which stats are tracked and finally sent to the stats_receiver future.

unsubscribe(subscriber: asyncutils._internal.prots.SpecificSubscriber, /, event_type: str) bool
unsubscribe(
subscriber: asyncutils._internal.prots.WildcardSubscriber,
/,
event_type: asyncutils._internal.prots.WildcardType = ...,
) bool

Remove a subscriber from the event bus under the event type (if unspecified, remove from wildcards) and return whether the removal occurred (i.e. the subscriber was initially present).

async wait_for_event(
event_type: str,
*,
timeout: bool | None = ...,
condition: collections.abc.Callable[[Any], object] = ...,
) asyncio.Task[Any]

Wait for an event of the specified event type that satisfies the condition to occur.

Note

The function completes once the subscription has registered and returns a task, which will be cancelled on timeout.

WILDCARD: asyncutils._internal.prots.WildcardType

Sentinel representing the event type of subscribers that accept any event name.

property active_tasks: int

The number of callbacks occurring at this moment.

property auditing: bool

Get-set property for is_auditing(). When changed, connect or disconnect the underlying audit hook accordingly.

property name: str

The name of the event bus.

property stream_queue: asyncio.Queue[Any]

An asynchronous queue of tuples (event_type, data) if the event type was not specified in the creation of the event stream, otherwise just the data attached to each event of that type, to which event_stream() outputs events.

property total_subscribers: int

The total number of subscribers for any event type.

property wildcard_count: int

The number of wildcard subscribers under this event bus.

property wildcards: weakref.WeakSet[asyncutils._internal.prots.WildcardSubscriber]

All the wildcard subscribers for this event bus.

class asyncutils.channels.Observable[**P](
init_observers: collections.abc.Iterable[asyncutils._internal.prots.Observer[P]],
maxsize: int | None = ...,
)
class asyncutils.channels.Observable(*, maxsize: int | None = ...)

Bases: asyncutils.mixins.LoopContextMixin

A class representing an observable stream of data, that observers can subscribe to and receive notifications from.

Attention

Observers must be hashable!

Caution

Use instances of this class as context managers only.

Instantiate the observable with the initial observers taken from the iterable init_observers. If maxsize is None, accumulation of notifications is disabled; otherwise, it is the maximum size of the queue of notifications (default is no maximum).

async __cleanup__() None
__iter__() types.GeneratorType[asyncutils._internal.prots.Observer[P]]

Iterate over the current observers. When this iterator is active, no subscriptions or unsubscriptions can be done.

async __setup__() None
at_change(key: collections.abc.Callable[P, object] = ..., ret_exc: bool = ...) Self

Return a new observable that will only emit notifications when the value returned by key changes.

buffer(count: int, ret_exc: bool = ...) Self

Return a new observable that will buffer notifications and emit them concurrently in batches of size count.

debounce(delay: float, ret_exc: bool = ...) Self

Return a new observable that will only emit the latest notification after delay seconds have passed since the last notification.

filter(pred: collections.abc.Callable[P, bool], ret_exc: bool = ...) Self

Return a new observable emitting the notifications of this observable to its observers only when the parameters, starred and passed to pred, evaluate to a true value.

fork(ret_exc: bool = ...) Self

Return a new observable that will emit all notifications to its observers.

async handle_notifications() None

Execute the queued notifications one by one and wait for each to complete.

async handle_unsubscriptions() None

Perform the unsubscriptions as requested by unsubscribe_eventually().

map(
transform: collections.abc.Callable[P, tuple[collections.abc.Iterable[object], collections.abc.Mapping[str, object]]],
ret_exc: bool = ...,
) Observable[Ellipsis]

Return a new observable transforming the parameters of notifications from this observable by transform.

merge(ret_exc: bool = ...) Self

Return a new observable that will emit notifications from all the observables in obs.

async notify(*a: P.args, **k: P.kwargs) None
async notify(*a: object, _ret_exc_: bool = ..., **k: object) None

Notify the observers with the parameters passed in. If another notification is in progress, it will be queued to be completed by that notification. If _ret_exc_ is True (default False), exceptions occurring in any observer is not propagated.

notify_sequential(*a: P.args, **k: P.kwargs) types.AsyncGeneratorType[Any]
notify_sequential(
*a: object,
_silent_: bool = ...,
_persistent_: bool = ...,
**k: object,
) types.AsyncGeneratorType[Any]

Version of notify() that doesn’t attempt to trigger the observers in parallel.

ntimes(observer: asyncutils._internal.prots.Observer[P], n: int = ...) asyncutils._internal.prots.SubscriptionRV

Add an observer immediately and automatically have it removed after n notifications. n defaults to OBSERVABLE_DEFAULT_NTIMES_N.

async restart_accumulation(flush: bool = ...) None

Complete all notifications if flush is True, then restart notification accumulation.

start_accumulation() bool

Begin accumulation of notifications and return True, or return False if accumulation is already occurring.

async subscribe(observer: asyncutils._internal.prots.Observer[P]) asyncutils._internal.prots.SubscriptionRV

Call wait_until_idle(), then add an observer and return a subscription object that can be used to remove it.

subscribe_nowait(observer: asyncutils._internal.prots.Observer[P]) asyncutils._internal.prots.SubscriptionRV

Add an observer without waiting for the observable to be idle.

subscribe_sync_func(observer: asyncutils._internal.prots.Observer[P]) asyncutils._internal.prots.SubscriptionRV

Subscribe a synchronous observer by converting it to async in an executor.

throttle(interval: float, ret_exc: bool = ...) Self

Return a new observable that will emit notifications at most once every interval seconds.

async unsubscribe(observer: asyncutils._internal.prots.Observer[P], strict: bool = ...) None

Call wait_until_idle(), then remove the observer. If strict is True, assert that the observer was indeed subscribed.

unsubscribe_eventually(observer: asyncutils._internal.prots.Observer[P], asap: bool = ...) None

Note that the observer is to be removed at some point in the future. If asap is True and there is no notification running, the observer is removed immediately.

unsubscribe_nowait(observer: asyncutils._internal.prots.Observer[P], strict: bool = ...) None

Remove the observer immediately even if a notification is occurring. If strict is True, assert that the observer was indeed subscribed.

async wait_for_next(timeout: float | None = ..., strict: bool = ...) tuple[tuple[Any, Ellipsis], dict[str, Any]]

Wait for the next notification to occur by adding a temporary subscriber and return its parameters as a tuple (args, kwargs). If strict is True, assert that another operation did not remove the subscriber prematurely.

async wait_until_idle(timeout: float | None = ...) None

Wait until the observable is idle, that is, until all notifications have completed.

property idle: bool

Whether the observable is idle, that is, not currently notifying observers.

property notifying: bool

The opposite of idle.

class asyncutils.channels.Rendezvous[T](*, loop: asyncio.AbstractEventLoop = ..., lock: asyncio.Lock = ...)

A rendezvous object, emulating Golang’s unbuffered channels.

Instantiate a rendezvous object, which will be maintained by a background task cleaning up its done getters and putters periodically, according to RENDEZVOUS_MAINTENANCE_INTERVAL.
If loop is not passed, the running event loop is used. If there is no running event loop, one is created and set.
__length_hint__() int

Approximate number of operations pending. Implemented for operator.length_hint().

cleanup() None

Clean up the internal getter and putter stacks.

async exchange(put_val: T, /, *, asap: bool = ...) T
Put in a value to the rendezvous and get and return a different value gotten from it.
If asap is True, return once a value is available, without necessarily having completed the put.
async get(default: T | None = ..., *, timeout: float | None = ...) T
Get a value from the rendezvous, blocking until available unless default is passed and timeout is not, in which case the default is returned if a value is not immediately available.
If default is not passed and timeout is reached, the TimeoutError is propagated. In any case, the get is cancelled at timeout.
async put(value: T, /, *, timeout: float | None = ...) bool

Like raising_put(), but returns a boolean representing if the put succeeded. The recommended interface.

async raising_put(value: T, /, *, timeout: float) None
Put in value to the rendezvous, blocking until it is gotten or timeout is reached, at which point TimeoutError is raised and the put cancelled.
Also be prepared to intercept or re-raise CancelledError resulting from reset.
async reset() None

Hard reset the rendezvous, cancelling all pending gets, puts and exchanges; their callers will see CancelledError. Call from a monitoring task when, for example, a deadlock appears to have occurred.

state_snapshot() asyncutils._internal.prots.StateSnapshot

Trigger a cleanup and return a snapshot of the current state of the object.

asyncutils.cli
Functions

run(→ int | None)

Module Contents
asyncutils.cli.run(argv: collections.abc.Iterable[str] | None = ...) int | None
Run this module’s REPL and return the integer return code.
If passed, argv should be a non-string iterable of strings representing the command-line arguments, and it should not have the executable name as the first item.
Otherwise, sys.argv is used, as per standard argparse behaviour.
An attempt will be made to parse all arguments and the program will exit entirely on an unrecognized option.
If an error somehow escapes the console and the pdb option is enabled, None will be returned after calling the post-mortem debugger on its traceback.

Execute asyncutils -?, or call get_cmd_help(), to see detailed command-line usage.

Warning

If you call this function manually, a daemon thread is spun up to execute the code in the console, which may still be kept alive by some internal mechanisms after the function returns. Worse still, if you call this function within another console, its standard input may completely cease to work.

asyncutils.compete
Functions

convert_to_coro_iter(…)

enhanced_gather(→ list[Any])

Version of asyncio.gather() that takes a larger variety of objects as the first argument, using convert_to_coro_iter() under the hood.

enhanced_staggered_race(→ tuple[Any, int | None, ...)

asyncio.staggered.staggered_race, but taking a larger variety of objects as the first argument using convert_to_coro_iter().

first_completed(…)

multi_winner_race_with_callback(→ list[T])

Return a list of all the coroutines that completed within timeout, and cancel the rest, triggering callbacks similarly to race_with_callback().

race_with_callback(→ T | None)

Module Contents
asyncutils.compete.convert_to_coro_iter(
cfs: asyncutils._internal.prots.SupportsIteration[Any],
*,
skip_invalid: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
corocheck: collections.abc.Callable[[Any], TypeIs[types.CoroutineType[Any, Any, Any]]],
futwrap: asyncutils._internal.prots.FutWrapType = ...,
handle_aiter: collections.abc.Callable[[collections.abc.AsyncIterable[Any]], types.CoroutineType[Any, Any, Any]] = ...,
handle_iter: collections.abc.Callable[[collections.abc.Iterable[Any]], types.CoroutineType[Any, Any, Any]] = ...,
) types.GeneratorType[types.CoroutineType[Any, Any, Any], Any]
asyncutils.compete.convert_to_coro_iter(
cfs: asyncutils._internal.prots.SupportsIteration[Any],
*,
skip_invalid: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
corocheck: collections.abc.Callable[[Any], TypeIs[collections.abc.Coroutine[Any, Any, Any]]] = ...,
futwrap: asyncutils._internal.prots.FutWrapType = ...,
handle_aiter: collections.abc.Callable[[collections.abc.AsyncIterable[Any]], collections.abc.Coroutine[Any, Any, Any]] = ...,
handle_iter: collections.abc.Callable[[collections.abc.Iterable[Any]], collections.abc.Coroutine[Any, Any, Any]] = ...,
) types.GeneratorType[collections.abc.Coroutine[Any, Any, Any], Any]
A helper function to convert a possibly async iterable of futures, coroutines and even (async) iterables cfs to a plain generator of coroutines, such that it may be starred and passed into the functions in this module.
Originally designed to complement asyncio.staggered.staggered_race.
Due to the possibility of cfs being async and this function being designed to operate in a sync context, it is somewhat inefficient.
skip_invalid, which determines whether to raise TypeError for inconvertible items or simply to skip them, defaults to CONVERT_TO_CORO_ITER_DEFAULT_SKIP_INVALID.
handle_aiter and handle_iter should be callables taking an async iterable and a sync iterable respectively and returning a coroutine.
async asyncutils.compete.enhanced_gather(
it: asyncutils._internal.prots.SupportsIteration[Any],
return_exceptions: bool = False,
*,
loop: asyncio.AbstractEventLoop | None = ...,
) list[Any]

Version of asyncio.gather() that takes a larger variety of objects as the first argument, using convert_to_coro_iter() under the hood.

See also

agather()

if you just want to pass in an async iterable; this version materializes a list of all the items within but avoids creating the intermediate concurrent.futures.Future’s, which in many cases is a better strategy

async asyncutils.compete.enhanced_staggered_race(
cfs: asyncutils._internal.prots.SupportsIteration[Any],
delay: float | None = ...,
*,
loop: asyncio.AbstractEventLoop | None = ...,
) tuple[Any, int | None, list[Exception | None]]

asyncio.staggered.staggered_race, but taking a larger variety of objects as the first argument using convert_to_coro_iter().

async asyncutils.compete.first_completed[T](
*C: collections.abc.Awaitable[T],
ret_exc: Literal[True],
timeout: float | None = ...,
) asyncutils._internal.prots.ExceptionWrapper | T | None
async asyncutils.compete.first_completed(
*C: collections.abc.Awaitable[T],
ret_exc: Literal[False] = ...,
timeout: float | None = ...,
) T | None
Return the result of the first coroutine that completes among those passed in.
If ret_exc is True, the coroutine might have errored, in which case the exception it throws is returned in a wrapped form unpackable using unwrap_exc() after checking with exception_occurred().
In any case, the losing coroutines are cancelled together and the function returns when the cancellations finish.
async asyncutils.compete.multi_winner_race_with_callback[T](
*C: collections.abc.Awaitable[T],
timeout: float,
winner: collections.abc.Callable[[T], object] = ...,
loser: collections.abc.Callable[[Any | BaseException], object] = ...,
) list[T]

Return a list of all the coroutines that completed within timeout, and cancel the rest, triggering callbacks similarly to race_with_callback().

async asyncutils.compete.race_with_callback[T](
*C: collections.abc.Awaitable[T],
winner: collections.abc.Callable[[T], object] = ...,
loser: collections.abc.Callable[[Any | BaseException], object] = ...,
timeout: float | None = ...,
) T | None
Return the result of the first coroutine to complete, which will have winner called on it.
If no coroutine completes within timeout, None is returned.
The loser callback is called on each return value of or exception raised by the losing coroutines after seeing CancelledError.
asyncutils.config

Set up some module-global state and sentinels, and expose some user-specified flags.

Attributes

basic_repl

Whether the user specified not to use the functions from _pyrepl to run the console, or they are on a Python version such that _pyrepl is not present or cannot be found such that the basic REPL must be used.

debug

A global instance of the Debugging context manager. Initially entered iff the user specified -d or --debug when starting the program.

loaded_all

Whether all submodules of this module have been loaded.

logging_to

The name of (i.e. possibly relative path to) the log file currently used by this library as a string, with four exceptions:

max_memory_errors

Maximum number of memory errors that can occur before the console automatically exits. Negative iff there is no maximum.

pdb

Whether the user specified to drop into the debugger on an unhandled exception in the REPL console.

silent

Whether the user requested to run the program with no banner and exit message in the REPL.

Exceptions

FaultyConfig

Raised when the user specifies a configuration value that is of the wrong type or otherwise invalid. This is basically impossible to catch, since it is only raised during the import of this module.

Classes

Debugging

A context manager used to enter and exit debug mode, ensuring restoration of the original level if the level has not been modified externally within the context using set_logger_level().

Executor

A class that implements the PEP 3148 executor interface.

Functions

get_past_logs(→ str)

Return all stored logs as a string. Logs are stored iff asyncutils was started with -l MEMORY, otherwise an empty string is returned.

set_logger_level(→ None)

Set the level of the module-global logger to level.

Module Contents
exception asyncutils.config.FaultyConfig(key: str, wrong: str, correct: tuple[str, Ellipsis], /)
exception asyncutils.config.FaultyConfig(key: str, wrong: T, correct: R, /)

Bases: BaseException

Raised when the user specifies a configuration value that is of the wrong type or otherwise invalid. This is basically impossible to catch, since it is only raised during the import of this module.

Initialize self. See help(type(self)) for accurate signature.

property key: str
class asyncutils.config.Debugging

A context manager used to enter and exit debug mode, ensuring restoration of the original level if the level has not been modified externally within the context using set_logger_level().

__enter__() Self

Start debugging. More output is produced; where to depends on the user’s own configuration, accessible via logging_to and debug.level.

__exit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
__exit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Stop debugging, restoring the output to its previous level if appropriate.

property entered: bool

Whether the context is entered.

property level: int

The current level of the asyncutils logger, as an integer.

property orig_level: int | None

The original logger level as an integer, before this context was entered, or None if it was not.

property orig_name: str | None

The original logger level name as a string, before this context was entered, or None if it was not.

class asyncutils.config.Executor

Bases: concurrent.futures.Executor, asyncutils._internal.prots.PartialInterface

A class that implements the PEP 3148 executor interface.

Note

The exact class is determined at runtime by command-line arguments.

Tip

Since instances of this class are only ever passed into run_in_executor(), nothing stops you from monkey-patching the event loop itself or policy thereof, and using a custom class that does not follow the interface, but that may be too hacky and fragile.

Tip

If you know your application only uses a specific executor, import this symbol at runtime and import the actual class in the stub or in an if TYPE_CHECKING: block where applicable to help type checkers.

asyncutils.config.get_past_logs() str

Return all stored logs as a string. Logs are stored iff asyncutils was started with -l MEMORY, otherwise an empty string is returned.

asyncutils.config.set_logger_level(level: int) None

Set the level of the module-global logger to level.

asyncutils.config.basic_repl: Final[bool]

Whether the user specified not to use the functions from _pyrepl to run the console, or they are on a Python version such that _pyrepl is not present or cannot be found such that the basic REPL must be used.

Deprecated since version 1.1.0: Will be removed when Python 3.12 support is dropped.

asyncutils.config.debug: Final[Debugging]

A global instance of the Debugging context manager. Initially entered iff the user specified -d or --debug when starting the program.

asyncutils.config.loaded_all: Final[bool]

Whether all submodules of this module have been loaded.

asyncutils.config.logging_to: Final[str]

The name of (i.e. possibly relative path to) the log file currently used by this library as a string, with four exceptions:

  • 'NULL': no logging is taking place

  • 'MEMORY': the logs are not going to a physical file but can be retrieved by get_past_logs()

  • 'STDOUT': logging is going to sys.stdout

  • 'STDERR': logging is going to sys.stderr (following the default and fallback behaviour of logging)

asyncutils.config.max_memory_errors: Final[int]

Maximum number of memory errors that can occur before the console automatically exits. Negative iff there is no maximum.

asyncutils.config.pdb: Final[bool]

Whether the user specified to drop into the debugger on an unhandled exception in the REPL console.

asyncutils.config.silent: Final[bool]

Whether the user requested to run the program with no banner and exit message in the REPL.

asyncutils.console

Implementation of an interactive async console base class, as well as an AsyncUtilsConsole class derived from it.

Classes

AsyncUtilsConsole

A subclass of ConsoleBase, used to implement the asyncutils REPL.

ConsoleBase

A base class for async consoles. Derives from InteractiveConsole, or _pyrepl.console.InteractiveColoredConsole if available. It is inspired by asyncio and highly adaptable.

Module Contents
class asyncutils.console.AsyncUtilsConsole(
loop: asyncio.AbstractEventLoop,
mod: types.ModuleType = ...,
modname: str = ...,
*,
context_factory: collections.abc.Callable[[], contextvars.Context] = ...,
)

Bases: ConsoleBase

A subclass of ConsoleBase, used to implement the asyncutils REPL.

  • loop (required): Event loop used by console interaction.

  • mod: The module to import within the console.

  • modname: The name of the above module, determined by the subclass name by default.

  • context_factory: A function that takes no arguments and returns an instance of contextvars.Context, to be used by the event loop.

_interact_hook(ps1: object, kcolour: str, reset: str, fcolour: str) None

Write code with emulated colour (such as import statements to represent the namespace) after the banner has been written, with parameters ps1 representing sys.ps1 and kcolour, reset and fcolour representing the ANSI escape codes for the keyword colour, colour reset and the function colour respectively.

after_run() None

Ensure the console is not left running after unset.

before_run(max_memory_errors: int | None) None

Ensure the console will be the only one running.

showtraceback() None

Display the formatted traceback of the exception being handled. If there was no exception, do nothing.

Note

This differs from the superclass behaviour, where AttributeError is raised outright.

write_special(msg: str) None

Write msg to stderr iff the quiet flag is not set.

property is_running: bool

Whether the console is currently running. Also performs internal state consistency checks, asserting that only one AsyncUtilsConsole can be running at a time.

class asyncutils.console.ConsoleBase(
loop: asyncio.AbstractEventLoop,
mod: types.ModuleType = ...,
modname: str = ...,
*,
context_factory: collections.abc.Callable[[], contextvars.Context] = ...,
)

Bases: code.InteractiveConsole, abc.ABC

A base class for async consoles. Derives from InteractiveConsole, or _pyrepl.console.InteractiveColoredConsole if available. It is inspired by asyncio and highly adaptable.

  • loop (required): Event loop used by console interaction.

  • mod: The module to import within the console.

  • modname: The name of the above module, determined by the subclass name by default.

  • context_factory: A function that takes no arguments and returns an instance of contextvars.Context, to be used by the event loop.

classmethod __init_subclass__(
*,
name: str = ...,
version: str = ...,
description: str = ...,
default_local_exit: bool = ...,
disallow_subclass_msg: str | None = ...,
native_handler: collections.abc.Callable[[dict[str, Any]], object] | None = ...,
other_handlers: dict[str, collections.abc.Callable[[dict[str, Any]], object] | None] = ...,
additional_interrupt_hooks: collections.abc.Iterable[collections.abc.Callable[[Self], object]] = ...,
additional_memory_error_hooks: collections.abc.Iterable[collections.abc.Callable[[Self], object]] = ...,
template: str = ...,
**k: object,
) None

All of the arguments below are optional.

  • name: name of the module using the console

  • version: version of the module using the console

  • description: description of the module using the console

  • default_local_exit, disallow_subclass_msg, native_handler, other_handlers, additional_interrupt_hooks, additional_memory_error_hooks: see above

  • template: the console banner to use, with %-placeholders for name, version and description

Additional keyword arguments are used to substitute %-placeholders in ``template``.

_interact_hook(ps1: object, kcolour: str, reset: str, fcolour: str) None

Write code with emulated colour (such as import statements to represent the namespace) after the banner has been written, with parameters ps1 representing sys.ps1 and kcolour, reset and fcolour representing the ANSI escape codes for the keyword colour, colour reset and the function colour respectively.

after_run() None
Finalize the interaction from run(). Called before writing the exit message. Should not raise errors.
It is highly recommended that subclasses implement this and call super().after_run() within the implementation after the custom logic.
abstractmethod before_run(max_memory_errors: int | None) None
Prepare for the interaction logic to begin in run(). Can raise errors.
When implementing, call super().before_run(max_memory_errors) before everything. This allows subclasses to pass their own value of max_memory_errors.
interact(banner: str | None = ..., *, ps1: object = ...) None

In the main thread, the run method is preferred.

interrupt() None

Pass additional_interrupt_hooks to the subclass constructor to change the behaviour when encountering a KeyboardInterrupt, instead of touching this method.

memory_error() None

Pass additional_memory_error_hooks to the subclass constructor to change the behaviour when encountering a MemoryError, instead of touching this method.

refresh() None

Cancel the internal future such that it no longer resolves to the result of an async call. Called by interrupt() and memory_error().

run(
*,
exit_message: str = ...,
thread_name: str = ...,
max_memory_errors: int = ...,
always_run_interactive: bool = ...,
always_install_completer: bool = ...,
suppress_asyncio_warnings: bool = ...,
suppress_unawaited_coroutine_warnings: bool = ...,
) int
Run the console and return the integer return code.
The strings exit_message and thread_name should support %-formatting, the placeholder being the module name.
Pass a negative value for max_memory_errors to disable the stop after certain number of MemoryError’s behaviour.
If always_install_completer is True, set the completer on readline as long as readline is available.
Pass True for suppress_asyncio_warnings and suppress_unawaited_coroutine_warnings to silence asyncio logging and warnings for garbage-collected coroutines not being awaited respectively.
If you wish the console to act like a console even when stdin is piped, pass always_run_interactive=True or start Python with the -i flag.
runcode(
code: types.CodeType,
*,
fimp: collections.abc.Callable[[], concurrent.futures.Future[Any]] = ...,
no_traceback: tuple[asyncutils._internal.prots.ExcType, Ellipsis] = ...,
threadsafe: bool = ...,
) Any | None
Run code, an instance of types.CodeType, as a callback managed by the event loop, and return its result, or STATEMENT_FAILED if the statement fails.
fimp is a function that returns an instance of concurrent.futures.Future.
no_traceback is a tuple of types of exceptions for which the traceback should not be shown if they are to occur.
threadsafe dictates whether to run the code in the event loop using call_soon_threadsafe() instead of call_soon().
set_return_code(exc: SystemExit, /) None
set_return_code(code: int | str, /) None

Set the return code of this console from an instance of SystemExit or an integer return code and exit the console.

showtraceback() None

Display the formatted traceback of the exception being handled. If there was no exception, do nothing.

Note

This differs from the superclass behaviour, where AttributeError is raised outright.

write_special(msg: str) None

Write the banner and exit messages. Can have a different implementation than write().

BANNER: ClassVar[str]

A %-formattable string representing the template of the banner to be shown when the console starts.

CAN_USE_PYREPL: ClassVar[bool]

Whether _pyrepl enhancements are available and allowed.

LOCALS_HANDLERS: ClassVar[collections.ChainMap[str, collections.abc.Callable[[dict[str, Any]], Any] | None]]
Maps module names to a function taking locals of a console of the corresponding type. The return value is discarded.
Add handlers for the module of your own console with native_handler and other modules with other_handlers.
NAME: ClassVar[str]

The name of the module implementing this console, detected from the class name if the keyword argument name is not provided to the subclass constructor.

property _internal_is_running: bool

Whether the console thinks itself is running. Can be used in is_running for state consistency checks.

property context: contextvars.Context

The contextvars.Context instance passed to methods of the underlying asyncio event loop.

default_local_exit: ClassVar[bool]

Whether Python should continue running after the console exits by default, as opposed to the console raising SystemExit directly.

disallow_subclass_msg: ClassVar[str]

The error message when attempts are made to subclass subclasses of this class. Specified through the disallow_subclass_msg argument, which any unsubclassable console should pass.

property exc: SystemExit | None

The SystemExit instance that caused the console to exit, or None if the console has not exited.

interrupt_hooks: ClassVar[tuple[collections.abc.Callable[[Self], Any], Ellipsis]]

Functions called when KeyboardInterrupt occurs, in that order, besides essential hardcoded logic.

Note

Add hooks using the additional_interrupt_hooks class construction parameter.

property is_running: bool

Whether the console is running. The default implementation simply returns _internal_is_running.

memory_error_hooks: ClassVar[tuple[collections.abc.Callable[[Self], Any], Ellipsis]]

Functions called when a MemoryError occurs, in that order, besides essential hardcoded logic.

Note

Add hooks using the additional_memory_error_hooks class construction parameter.

property memory_errors: int

The number of MemoryError’s that have occurred.

asyncutils.constants

Exports sentinels and public constants.

Attributes

EXECUTORS_FROZENSET

Equivalent to frozenset(POSSIBLE_EXECUTORS), so that there can be faster membership testing.

NO_COALESCE

Sentinel requesting coalesce() not to combine two adjacent values.

POSSIBLE_EXECUTORS

A tuple of all possible executor names that can be passed to -e, in rough order of preference and popularity. Also the order in which the executor options appear in the CLI help.

RAISE

Sentinel requesting an error be raised in some cases. Can only be passed to functions that are documented to support it.

RECIPROCAL_E

The reciprocal of Euler's number, used by aguessmin() and aguessmax().

Classes

SentinelBase

Base class for sentinel values. To support versions below Python 3.15, we cannot make use of the PEP 661 built-in sentinel type, and this class offers extra methods anyway.

Module Contents
class asyncutils.constants.SentinelBase

Base class for sentinel values. To support versions below Python 3.15, we cannot make use of the PEP 661 built-in sentinel type, and this class offers extra methods anyway.

classmethod __init_subclass__(*, lock_impl: collections.abc.Callable[[], threading.Lock] = ...) None

lock_impl is a callable that takes no arguments and returns a _synchronous_ lock (e.g. allocate_lock()).

__reduce__() tuple[type[Self], tuple[str]]

Support for pickling.

__set_name__(owner: type, name: str, /) None

Bind the sentinel to a class and assign its name, if no arguments were passed to the constructor.

property back: str | None

The unqualified name of the sentinel, or None if there is none.

property bound_to: str | None

The name of the class the sentinel is bound to, or None if there is none.

property is_private: bool

Whether the sentinel is private; that is, the name begins with underscore.

property module: str

The name of the module the sentinel is defined in.

property name: str

Fully qualified name of the sentinel, the only thing that identifies it uniquely. May not be present if improperly instantiated.

asyncutils.constants.EXECUTORS_FROZENSET: Final[frozenset[asyncutils._internal.prots.Executor]]

Equivalent to frozenset(POSSIBLE_EXECUTORS), so that there can be faster membership testing.

asyncutils.constants.NO_COALESCE: Final[asyncutils._internal.prots.NoCoalesce]

Sentinel requesting coalesce() not to combine two adjacent values.

asyncutils.constants.POSSIBLE_EXECUTORS: Final[tuple[asyncutils._internal.prots.Executor, Ellipsis]]

A tuple of all possible executor names that can be passed to -e, in rough order of preference and popularity. Also the order in which the executor options appear in the CLI help.

asyncutils.constants.RAISE: Final[asyncutils._internal.prots.Raise]

Sentinel requesting an error be raised in some cases. Can only be passed to functions that are documented to support it.

asyncutils.constants.RECIPROCAL_E: Final[float]

The reciprocal of Euler’s number, used by aguessmin() and aguessmax().

asyncutils.context

Contextual configuration system, inspired by the decimal module.

Attributes

all_contextual_consts

A frozenset of all contextual constant names, for use in validating that only valid contextual constants are accessed or modified.

Classes

Context

LocalContext

Context manager that temporarily sets the context of the current thread to a modified version of the provided context. Not re-entrant, but reusable with the exact same new_ctx.

NonReusableLocalContext

Version of LocalContext that is not reusable. Use this to avoid subtle bugs, especially since it's not that expensive to instantiate a Context.

Functions

getcontext(→ Context)

Return the current context for the active thread.

setcontext(→ None)

Set the current context to for the active thread to ctx.

Module Contents
class asyncutils.context.Context
An object storing configuration for various functions and patterns in this library, for immutability and performance; that is, not loading dataclasses for dataclass(), which loads inspect, triggering a cascade of imports.
namedtuple() is also unsuitable for this use case, since it behaves like a sequence.
The order of the fields are kept in alphabetical order of submodule and in each submodule, and new fields may be added in the future.
For consistency, each field is named in all caps with words separated by underscores, and prefixed by the name of the utility it is used in, followed by a concise description of what it configures.

Tip

If you need to use any of the settings, you can find the documentation under the API reference for the utilities that use that setting.

Note

Refer to config for the factory default values of each setting.

Note

It is possible, but discouraged, to access these fields with attribute names that are not all uppercase.

Note

This is only type annotated as a dataclass for convenience. It is a regular class at runtime.

__copy__() Self

Alias for copy().

__eq__(other: object, /) bool

Two contexts are considered equal if they are of the same type and all of their fields are equal.

__getitem__(name: str, /) Any

Context’s also behave like mappings.

__setitem__(name: str, value: object, /) None

Alias for __setattr__().

ascurctx(**k: object) NonReusableLocalContext

Return a non-reusable context manager that sets the context to this context on entry. For some Context ctx, ctx.ascurctx() is syntactic sugar for NonReusableLocalContext(ctx).

asdict() dict[str, Any]

Return a dictionary representing the items within the context.

copy() Self

Return a shallow copy of the context.

classmethod from_dct(dct: dict[str, Any], /) Self

Build an instance from the keys of the dictionary.

pprint(
file: asyncutils._internal.prots.CanWriteAndFlush[str] = ...,
*,
pp: pprint.PrettyPrinter = ...,
include_newline: bool = ...,
) None

Pretty print the context to the provided file-like object file with the pprint.PrettyPrinter instance pp, without a trailing newline if include_newline=False is specified.

replace(/, **k: object) Self

Return a new instance with the same values as this one besides the keyword arguments.

replace_from_dct(dct: dict[str, Any], /) Self

Return a new instance with the same values as this one besides the keys of dct.

update(dct: dict[str, Any] = ..., /, **k: object) None

Update the values of the instance with dct if passed, then the keyword arguments.

ADVANCED_POOL_DEFAULT_MAX_WORKERS: int = Ellipsis
ADVANCED_POOL_DEFAULT_MIN_WORKERS: int = Ellipsis
ADVANCED_POOL_FACTOR: float = Ellipsis
ADVANCED_POOL_THRESHOLD_HI: float = Ellipsis
ADVANCED_POOL_THRESHOLD_LO: float = Ellipsis
ADVANCED_RATE_LIMIT_DEFAULT_TOKENS: float = Ellipsis
AFREIVALDS_DEFAULT_K: int = Ellipsis
AGING_RWLOCK_DEFAULT_READ_PRIORITY_FACTOR: float = Ellipsis
AGING_RWLOCK_DEFAULT_WRITE_PRIORITY_FACTOR: float = Ellipsis
AITER_TO_GEN_DEFAULT_ALLOW_FUTURES: bool = Ellipsis
AITER_TO_GEN_DEFAULT_STRICT: bool = Ellipsis
AONLINE_SORTER_DEFAULT_SLOW: bool = Ellipsis
AUNZIP_DEFAULT_MAX_QSIZE: int = Ellipsis
AUNZIP_DEFAULT_PUT_BATCH: int = Ellipsis
BACKGROUND_REFRESH_CACHE_DEFAULT_REFRESH: float = Ellipsis
BACKGROUND_REFRESH_CACHE_DEFAULT_TTL: float = Ellipsis
BATCH_PROCESSOR_DEFAULT_MAX_SIZE: int = Ellipsis
BATCH_PROCESSOR_DEFAULT_MAX_TIME: float = Ellipsis
BENCHMARK_DEFAULT_SEQUENTIAL: bool = Ellipsis
BENCHMARK_DEFAULT_TIMES: int = Ellipsis
BENCHMARK_DEFAULT_WARMUP: int = Ellipsis
BOUNDED_BATCH_PROCESSOR_DEFAULT_BATCH_SIZE: int = Ellipsis
BOUNDED_BATCH_PROCESSOR_DEFAULT_MAX_CONCURRENT: int = Ellipsis
BULKHEAD_DEFAULT_MAX_QUEUE: int = Ellipsis
BULKHEAD_DEFAULT_MAX_REJ: int = Ellipsis
CIRCUIT_BREAKER_DEFAULT_MAX_FAILS: int = Ellipsis
CIRCUIT_BREAKER_DEFAULT_MAX_HALF_OPEN_CALLS: int = Ellipsis
CIRCUIT_BREAKER_DEFAULT_RESET: float = Ellipsis
CONNECTION_POOL_DEFAULT_MAX_LIFE: float = Ellipsis
CONNECTION_POOL_DEFAULT_MAX_SIZE: int = Ellipsis
CONNECTION_POOL_DEFAULT_MIN_SIZE: int = Ellipsis
CONNECTION_POOL_MAINTENANCE_INTERVAL: float = Ellipsis
CONVERT_TO_CORO_ITER_DEFAULT_SKIP_INVALID: bool = Ellipsis
DUAL_CONTEXT_MANAGER_DEFAULT_MAY_CREATE_EXECUTOR: bool = Ellipsis
DUAL_CONTEXT_MANAGER_DEFAULT_STRICT: bool = Ellipsis
DUAL_CONTEXT_MANAGER_DEFAULT_USE_EXISTING_EXECUTOR: bool = Ellipsis
DYNAMIC_BOUNDED_SEMAPHORE_DEFAULT_VALUE: int = Ellipsis
DYNAMIC_THROTTLE_DEFAULT_JITTER: float = Ellipsis
DYNAMIC_THROTTLE_DEFAULT_LBOUND: float = Ellipsis
DYNAMIC_THROTTLE_DEFAULT_LFACTOR: float = Ellipsis
DYNAMIC_THROTTLE_DEFAULT_MAX_RATE: float = Ellipsis
DYNAMIC_THROTTLE_DEFAULT_MIN_RATE: float = Ellipsis
DYNAMIC_THROTTLE_DEFAULT_UBOUND: float = Ellipsis
DYNAMIC_THROTTLE_DEFAULT_UFACTOR: float = Ellipsis
DYNAMIC_THROTTLE_DEFAULT_WINDOW: int = Ellipsis
EVENT_BUS_DEFAULT_MAX_CONCURRENT: int = Ellipsis
EVENT_BUS_PUBLISH_DEFAULT_SAFE: bool = Ellipsis
EVENT_BUS_STREAM_DEFAULT_BUFFER_SIZE: int = Ellipsis
EVENT_BUS_STREAM_DEFAULT_ITEM_TIMEOUT: float | None = Ellipsis
EVENT_BUS_STREAM_DEFAULT_TIMEOUT: float | None = Ellipsis
EVENT_LOOP_BASE_FLAGS: int = Ellipsis
EVENT_WITH_VALUE_DEFAULT_MAX_HIST: int = Ellipsis
EVENT_WITH_VALUE_DEFAULT_RECENT: float = Ellipsis
GATHER_WITH_LIMITED_CONCURRENCY_DEFAULT_MAX_CONCURRENT: int = Ellipsis
ITER_TO_AGEN_DEFAULT_MAY_CREATE_EXECUTOR: bool = Ellipsis
ITER_TO_AGEN_DEFAULT_STRICT: bool = Ellipsis
ITER_TO_AGEN_DEFAULT_USE_EXISTING_EXECUTOR: bool = Ellipsis
LEAKY_BUCKET_ADJMAP: collections.abc.Sequence[tuple[float, tuple[float, float, float, float]]] = Ellipsis
LEAKY_BUCKET_DEFAULT_ACQUIRE_TOKENS: float = Ellipsis
LEAKY_BUCKET_DEFAULT_EXT_CAN_SET_FACTOR: bool = Ellipsis
LEAKY_BUCKET_DEFAULT_MAX_FACTOR: float = Ellipsis
LEAKY_BUCKET_DEFAULT_MIN_FACTOR: float = Ellipsis
LEAKY_BUCKET_DEFAULT_WAIT_FOR_TOKENS_TOKENS: float = Ellipsis
LEAKY_BUCKET_WAIT_FOR_TOKENS_TICK: float = Ellipsis
LINE_PROTOCOL_DEFAULT_BUFFER_SIZE: int = Ellipsis
LOCKSMITH_BASE_DEFAULT_TIMEOUTS: tuple[float | None, float | None, float | None] = Ellipsis
MAKE_TASK_FACTORY_DEFAULT_EAGER: bool = Ellipsis
MEMORY_MAPPED_IO_MANAGER_DEFAULT_CHECKSUM_ALG: asyncutils._internal.prots.HashAlgorithm = Ellipsis
MEMORY_MAPPED_IO_MANAGER_DEFAULT_MINIMIZE_WRITES: bool = Ellipsis
MERGE_DEFAULT_MAX_QSIZE: int = Ellipsis
OBSERVABLE_DEFAULT_NTIMES_N: int = Ellipsis
PASSWORD_QUEUE_DEFAULT_GET_FROM: str = Ellipsis
PASSWORD_QUEUE_DEFAULT_PUT_FROM: str = Ellipsis
PRIORITY_SEMAPHORE_DEFAULT_VALUE: int = Ellipsis
RENDEZVOUS_MAINTENANCE_INTERVAL: float = Ellipsis
RETRY_DEFAULT_BACKOFF: float = Ellipsis
RETRY_DEFAULT_DELAY: float = Ellipsis
RETRY_DEFAULT_JITTER: float = Ellipsis
RETRY_DEFAULT_MAX_DELAY: float = Ellipsis
RETRY_DEFAULT_TRIES: int = Ellipsis
RWLOCK_DEFAULT_PREFER_WRITERS: bool = Ellipsis
SEMAPHORE_DEFAULT_VALUE: int = Ellipsis
SOCKET_TRANSPORT_LIMITS: tuple[int, int] = Ellipsis
TEE_DEFAULT_MAX_QSIZE: int = Ellipsis
TEE_DEFAULT_PUT_EXC: bool = Ellipsis
TIMER_DEFAULT_PRECISION: int = Ellipsis
TOKEN_BUCKET_DEFAULT_CONSUME_TOKENS: float = Ellipsis
WAIT_FOR_SIGNAL_DEFAULT_SIGNALS: collections.abc.Sequence[int] = Ellipsis
__hash__: ClassVar[None]

Contexts are not hashable since they are mutable.

class asyncutils.context.LocalContext(ctx: Context = ..., **k: object)

Context manager that temporarily sets the context of the current thread to a modified version of the provided context. Not re-entrant, but reusable with the exact same new_ctx.

Note that the context of the current thread is to be set to a shallow copy of ctx, defaulting to the current context, with replacements from the keyword arguments.

async __aenter__() Context

Return the new context after setting it.

async __aexit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Reset the context to the previous.

__enter__() Context

Return the new context after setting it.

__exit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
__exit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Reset the context to the previous.

property new_ctx: Context

The new context to be set on context manager entry.

property saved_ctx: Context

The previous context to be restored on context manager exit.

class asyncutils.context.NonReusableLocalContext(ctx: Context = ..., **k: object)

Bases: LocalContext

Version of LocalContext that is not reusable. Use this to avoid subtle bugs, especially since it’s not that expensive to instantiate a Context.

Note that the context of the current thread is to be set to a shallow copy of ctx, defaulting to the current context, with replacements from the keyword arguments.

asyncutils.context.getcontext() Context

Return the current context for the active thread.

asyncutils.context.setcontext(ctx: Context, /) None

Set the current context to for the active thread to ctx.

asyncutils.context.all_contextual_consts: frozenset[str]

A frozenset of all contextual constant names, for use in validating that only valid contextual constants are accessed or modified.

Note

These names are not listed by calling dir() on this submodule, since there are so many of them (87 as of now!) and more may be added in the future, and the recommended way to get their values is to query them on the actual context object anyway. However, they are still provided below to facilitate type checking.

asyncutils.events
Classes that extend the functionality of Event with the interface it specifies, without inheriting from it.
Not at all related to asyncio.events, which manages the event loop, despite the common name.
Classes

EventWithValue

An event class that can store a value and maintains a history of past values.

SingleWaiterEventWithValue

Essentially wraps a future in the event interface.

Module Contents
class asyncutils.events.EventWithValue[T: asyncutils._internal.prots.NotNone](*, maxhist: int | None = ...)

Bases: asyncutils.mixins.EventMixin[T]

An event class that can store a value and maintains a history of past values.

Store a maximum of maxhist entries, which defaults to EVENT_WITH_VALUE_DEFAULT_MAX_HIST, of past results.

clear() None

Unset the result of the event.

get(default: T = ...) T

Get the result of the event immediately if set, otherwise returning default if passed or throw RuntimeError.

is_set() bool

Whether the result is currently set.

recent_history(duration: float | None = ...) types.GeneratorType[tuple[float, T]]

Yield recent history entries in order; what qualifies as recent depends on duration, defaulting to EVENT_WITH_VALUE_DEFAULT_RECENT.

remove_done_waiters() None

Clean up the internal queue of waiters, removing those having already completed. Should be run periodically.

set(value: None, *, strict: Literal[False]) None
set(value: T, *, strict: bool = ...) None

Set the result of the event and wake up waiters. If strict is True, throws an error when the value is None, since it is more idiomatic to call clear() instead.

set_once(value: T) None

Set the result to value, and then immediately revert it to the original. Waiters are triggered twice.

async wait_for_next(timeout: float | None = ...) T

Wait for the next result of the event to be set.

async wait_for_transition(
old: T,
new: T,
timeout: float | None = ...,
*,
force_transition: bool = ...,
legacy: bool = ...,
) bool
Wait until the value is set to old, and then new, in that order.
On timeout, if force_transition is True, cause the transition to happen manually.
If legacy=True is passed, overlapping potential transitions resulting wait_for_next() returning the same value twice in a row, are not considered, as per the old behaviour.
Return whether the transition occurred naturally.
async wait_for_transition_unordered(
a: T,
b: T,
timeout: float | None = ...,
*,
force_transition: bool = ...,
legacy: bool = ...,
) bool

Wait until either a transitions to b or b transitions to a, with the preference being for the former.

property history: list[tuple[float, T]]

The past results of the event as a list of tuples (timestamp, value).

property history_asdict: dict[float, T]

Above, but as a dictionary.

class asyncutils.events.SingleWaiterEventWithValue[T]

Bases: asyncutils.mixins.EventMixin[T]

Essentially wraps a future in the event interface.

clear() None

Unset the result of the event.

get(default: T = ...) T

Get the result of the event immediately if set, otherwise returning default if passed or throw RuntimeError.

is_set() bool

Whether the result is currently set.

set(value: T) None

Set the result of the event to value, awakening the sole waiter.

async wait(timeout: float | None = ..., *, strict: bool = ...) T
async wait_for_next(timeout: float | None = ..., *, strict: bool = ...) T

Wait for the next result of the event to be set.

asyncutils.exceptions

Exception handling utilities and exception classes used by this module.

Attributes

CRITICAL

The tuple (SystemExit, SystemError, KeyboardInterrupt), representing exceptions that should be allowed to propagate under most error handling mechanisms.

ignore_all

Instance of IgnoreErrors that ignores all errors; that is, IgnoreErrors(BaseException). Use with caution!

ignore_noncritical

Instance of IgnoreErrors that ignores all errors besides SystemExit, SystemError and KeyboardInterrupt. Equivalent to ignore_all.excluding(*CRITICAL).

ignore_stop_async_iteration

Instance of IgnoreErrors that ignores StopAsyncIteration. Equivalent to IgnoreErrors(StopAsyncIteration).

ignore_stop_iteration

Instance of IgnoreErrors that ignores StopIteration. Equivalent to IgnoreErrors(StopIteration).

ignore_typeerrs

Instance of IgnoreErrors that ignores TypeError. Equivalent to IgnoreErrors(TypeError).

ignore_typical

Instance of IgnoreErrors that ignores Exception and subclasses thereof. Equivalent to IgnoreErrors().

ignore_valerrs

Instance of IgnoreErrors that ignores ValueError. Equivalent to IgnoreErrors(ValueError).

ignore_warnings

Instance of IgnoreErrors that ignores Warning. Equivalent to IgnoreErrors(Warning).

Exceptions

BulkheadError

Raised when there is an error in bulkhead processing.

BulkheadFull

Raised when a bulkhead is full and a party requests it to execute a coroutine.

BulkheadShutDown

Raised when a bulkhead is being shut down and a party requests it to execute a coroutine.

BusError

Raised when an operation on an EventBus fails.

BusPublishingError

Raised when an event bus fails to publish an event.

BusShutDown

Raised when subscription or publishing operations are called on an EventBus that is closing down.

BusStatsError

Raised when attempting to access publishing statistics on an EventBus whose statistics are not tracked.

BusTimeout

Raised when an EventBus takes too long to publish an event.

CircuitBreakerError

Base class for circuit breaker errors.

CircuitHalfOpen

Raised when a circuit exceeds its maximum calls in the half-open state.

CircuitOpen

Raised when a circuit is open in a CircuitBreaker (but shouldn't be).

Critical

Raised when a critical error is encountered by exception-handling middleware.

Deadlock

Raised when a deadlock is detected. Should not be caught by users.

EventValueError

Raised when a party attempts to get the value an event of which the value is not set.

ForbiddenOperation

A forbidden operation was attempted on a password-protected queue.

FutureCorrupted

Raised after an internal party discovers an external party has set the result of a future whose result is for it to set only.

GetPasswordMissing

The get password was not passed to the get methods of a get-protected queue.

GetPasswordRetrievalError

Raised when password_queue() cannot find the get password from the closure variables.

ItemsExhausted

Raised when an asynchronous iterable runs out of items to take or collect.

LockForceRequest

Thrown to coroutines that acquire locks when a locksmith (inheriting from LocksmithBase) necessitates the lock be released.

MaxIterationsError

Raised when a function has reached the specified maximum iterations.

MoreThanOne

Raised when at_most_one() finds more than one item in the iterable it was passed.

PasswordError

Raised when the wrong password is provided to the get or put methods of a password-protected queue.

PasswordMissing

Base class of GetPasswordMissing and PutPasswordMissing.

PasswordQueueError

Base class for all errors related to password-protected queues, as returned by password_queue().

PasswordRetrievalError

Raised when password_queue() cannot find the password from the closure variables.

PoolError

Raised when a task pool encounters a miscellaneous error.

PoolFull

Raised when the task queue in a task pool is filled.

PoolShutDown

Raised when submissions are sent to a shutting down pool.

PutPasswordMissing

The put password was not passed to the put methods of a put-protected queue.

PutPasswordRetrievalError

Raised when password_queue() cannot find the put password from the closure variables.

RateLimitExceeded

Raised when a call to a function exceeds its rate limit and waiting is not allowed.

ResourceBusy

Raised when a party attempts to use a resource guarded actively by a ResourceGuard.

StateCorrupted

Raised when the module-internal state is corrupted. Should not be caught by users.

VersionConversionError

Base class for errors thrown when attempting to normalize an object to a version.

VersionCorrupted

Raised when internal state consistency checks of a version fail, indicating modifications by the user affected private state.

VersionError

Base class for all version-related errors.

VersionNormalizerFault

Wraps any errors thrown by a custom normalizer, intentionally or otherwise.

VersionNormalizerMissing

Raised when no normalizer is registered for an unrecognized object.

VersionNormalizerTypeError

Raised when a custom normalizer returns anything but an iterable of integers.

VersionValueError

Raised when an argument passed to the VersionInfo constructor is negative, for instance.

WrongPassword

Raised when the wrong password of the correct type is provided to the get or put methods of a password-protected queue.

WrongPasswordType

Raised when the password provided to the get or put methods of a password-protected queue is of the incorrect type.

Classes

IgnoreErrors

Context manager to suppress errors of the specified types and exit once they occur; works in both sync and async. More customizable than contextlib.suppress(), because some exception classes can be excluded from the suppression.

WarningToError

Context manager to convert specific warnings to errors; works in both sync and async.

Functions

exception_occurred(...)

Whether the object is actually a special proxy to an exception.

potent_derive(…)

prepare_exception(→ T)

raise_exc(…)

Programmatically raise an exception. The variadic args and kwargs are passed to the constructor of exc_typ in the first overload, and the remaining arguments are as in potent_derive().

unnest(→ types.GeneratorType[BaseException, BaseException])

unnest_reverse(→ types.GeneratorType[BaseException, ...)

Basically the above but in reverse order, with rare edge cases. More memory- and time-efficient than unnest.

unwrap_exc(→ BaseException)

Recover the exception wrapped by wrap_exc(). This function does not raise the exception because it may sometimes be useful to have the exception object itself, for example when setting it on a Future.

wrap_exc(→ asyncutils._internal.prots.ExceptionWrapper)

Wrap an exception in a special proxy wrapper, such that exception_occurred(wrapper) returns True.

Module Contents
exception asyncutils.exceptions.BulkheadError

Bases: RuntimeError

Raised when there is an error in bulkhead processing.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.BulkheadFull

Bases: BulkheadError

Raised when a bulkhead is full and a party requests it to execute a coroutine.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.BulkheadShutDown

Bases: BulkheadError

Raised when a bulkhead is being shut down and a party requests it to execute a coroutine.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.BusError

Bases: RuntimeError

Raised when an operation on an EventBus fails.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.BusPublishingError(bus: asyncutils.channels.EventBus, mw: asyncutils._internal.prots.Middleware, /)

Bases: BusError

Raised when an event bus fails to publish an event.

Initialize self. See help(type(self)) for accurate signature.

property bus: asyncutils.channels.EventBus | None

May be None if the event bus was garbage-collected.

property middleware: asyncutils._internal.prots.Middleware | None

May be None if the middleware was garbage-collected.

exception asyncutils.exceptions.BusShutDown

Bases: BusError

Raised when subscription or publishing operations are called on an EventBus that is closing down.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.BusStatsError

Bases: BusError

Raised when attempting to access publishing statistics on an EventBus whose statistics are not tracked.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.BusTimeout

Bases: BusError

Raised when an EventBus takes too long to publish an event.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.CircuitBreakerError

Bases: RuntimeError

Base class for circuit breaker errors.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.CircuitHalfOpen

Bases: CircuitBreakerError

Raised when a circuit exceeds its maximum calls in the half-open state.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.CircuitOpen

Bases: CircuitBreakerError

Raised when a circuit is open in a CircuitBreaker (but shouldn’t be).

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.Critical[T: (SystemExit, SystemError, KeyboardInterrupt)](exc: T)
exception asyncutils.exceptions.Critical(exc: None = ...)

Bases: BaseException

Raised when a critical error is encountered by exception-handling middleware.

Initialize the critical exception with the exception being wrapped, or the currently handled exception if not passed.

property exc: T

The exception that occurred, determined by the raising scope by default.

exception asyncutils.exceptions.Deadlock

Bases: BaseException

Raised when a deadlock is detected. Should not be caught by users.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.EventValueError

Bases: ValueError

Raised when a party attempts to get the value an event of which the value is not set.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.ForbiddenOperation(op: str, *a: object)

Bases: PasswordQueueError, TypeError

A forbidden operation was attempted on a password-protected queue.

Substitute in the arguments to the string (if any) to derive the name of the forbidden operation.

property op: str

A string representing the operation type.

exception asyncutils.exceptions.FutureCorrupted

Bases: RuntimeError

Raised after an internal party discovers an external party has set the result of a future whose result is for it to set only.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.GetPasswordMissing

Bases: PasswordMissing

The get password was not passed to the get methods of a get-protected queue.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.GetPasswordRetrievalError(from_: str)

Bases: PasswordRetrievalError

Raised when password_queue() cannot find the get password from the closure variables.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.ItemsExhausted

Bases: ValueError

Raised when an asynchronous iterable runs out of items to take or collect.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.LockForceRequest[T, S: asyncutils._internal.prots.AsyncLockLike[Any], R: asyncutils.locksmiths.LocksmithBase](requester: R, fulfil: collections.abc.Callable[[Any], None], lock: S, info: T, /)

Bases: BaseException

Thrown to coroutines that acquire locks when a locksmith (inheriting from LocksmithBase) necessitates the lock be released.

Initialize self. See help(type(self)) for accurate signature.

fulfil(answer: object, /) None

Answer the request with answer, after presumably releasing the lock and performing error handling.

property info: T

The info passed to the force() method, or as returned by get_info(). Coerced to str as a note attached on this exception when traceback prints it.

property lock: S

The lock involved.

property requester: R

The locksmith that sent this error.

exception asyncutils.exceptions.MaxIterationsError

Bases: RuntimeError

Raised when a function has reached the specified maximum iterations.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.MoreThanOne[T](it: types.AsyncGeneratorType[T], msg: str, /)

Bases: ValueError

Raised when at_most_one() finds more than one item in the iterable it was passed.

Initialize self. See help(type(self)) for accurate signature.

property it: types.AsyncGeneratorType[T]

An async iterator over the original iterable. The second item is the offending item.

exception asyncutils.exceptions.PasswordError[T]

Bases: PasswordQueueError

Raised when the wrong password is provided to the get or put methods of a password-protected queue.

Initialize self. See help(type(self)) for accurate signature.

property qid: int

The memory address of the queue associated with the exception. Invalid if the queue has been garbage collected.

property wrong_pwd: T

The wrong password associated with the exception. May be None if the wrong password has been garbage collected.

exception asyncutils.exceptions.PasswordMissing

Bases: PasswordQueueError, TypeError

Base class of GetPasswordMissing and PutPasswordMissing.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.PasswordQueueError

Bases: Exception

Base class for all errors related to password-protected queues, as returned by password_queue().

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.PasswordRetrievalError(from_: str)

Bases: PasswordQueueError

Raised when password_queue() cannot find the password from the closure variables.

Initialize self. See help(type(self)) for accurate signature.

property from_: str

The specified name of the closure variable.

exception asyncutils.exceptions.PoolError

Bases: RuntimeError

Raised when a task pool encounters a miscellaneous error.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.PoolFull

Bases: PoolError

Raised when the task queue in a task pool is filled.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.PoolShutDown

Bases: PoolError

Raised when submissions are sent to a shutting down pool.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.PutPasswordMissing

Bases: PasswordMissing

The put password was not passed to the put methods of a put-protected queue.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.PutPasswordRetrievalError(from_: str)

Bases: PasswordRetrievalError

Raised when password_queue() cannot find the put password from the closure variables.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.RateLimitExceeded

Bases: RuntimeError

Raised when a call to a function exceeds its rate limit and waiting is not allowed.

Implementation detail

The initialization signature may change without notice, and is therefore not documented here.

Initialize self. See help(type(self)) for accurate signature.

async repeat_call() Any

Repeat the call to the function that exceeded the rate limit without the rate limiter.

exception asyncutils.exceptions.ResourceBusy

Bases: RuntimeError

Raised when a party attempts to use a resource guarded actively by a ResourceGuard.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.StateCorrupted(adjective: str, details: str, /)

Bases: BaseException

Raised when the module-internal state is corrupted. Should not be caught by users.

Initialize self. See help(type(self)) for accurate signature.

property adjective: str
property details: str
exception asyncutils.exceptions.VersionConversionError

Bases: VersionError

Base class for errors thrown when attempting to normalize an object to a version.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.VersionCorrupted(obj: asyncutils.version.VersionInfo, /)

Bases: VersionError, RuntimeError

Raised when internal state consistency checks of a version fail, indicating modifications by the user affected private state.

Initialize self. See help(type(self)) for accurate signature.

__getattr__(name: str, /) Any
property obj: asyncutils.version.VersionInfo | None

The instance of VersionInfo having been corrupted. None if garbage collected.

exception asyncutils.exceptions.VersionError

Bases: Exception

Base class for all version-related errors.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.VersionNormalizerFault[T](
normalizer: collections.abc.Callable[[T], collections.abc.Iterable[int]],
obj: T,
exc: BaseException,
/,
)

Bases: VersionConversionError

Wraps any errors thrown by a custom normalizer, intentionally or otherwise.

Initialize self. See help(type(self)) for accurate signature.

property exc: BaseException | None

The exception thrown. None if garbage collected.

property normalizer: collections.abc.Callable[[T], collections.abc.Iterable[int]] | None

The normalizer at fault. None if garbage collected.

property obj: T | None

The handled object. None if garbage collected.

exception asyncutils.exceptions.VersionNormalizerMissing[T](obj: T, /)

Bases: VersionConversionError, TypeError

Raised when no normalizer is registered for an unrecognized object.

Initialize self. See help(type(self)) for accurate signature.

property obj: T | None

The unrecognized object. None if garbage collected.

exception asyncutils.exceptions.VersionNormalizerTypeError[T](normalizer: collections.abc.Callable[[T], object], obj: T, /)

Bases: VersionConversionError, TypeError

Raised when a custom normalizer returns anything but an iterable of integers.

Initialize self. See help(type(self)) for accurate signature.

property normalizer: collections.abc.Callable[[T], Any] | None

The normalizer at fault. None if garbage collected.

property obj: T | None

The object being normalized by the normalizer, for which a value of incorrect type was returned. None if garbage collected.

exception asyncutils.exceptions.VersionValueError

Bases: VersionConversionError, ValueError

Raised when an argument passed to the VersionInfo constructor is negative, for instance.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.WrongPassword[T](queue: asyncutils._internal.prots.QProtBase[Any, Any], pwd: T, /)

Bases: PasswordError[T], ValueError

Raised when the wrong password of the correct type is provided to the get or put methods of a password-protected queue.

Initialize self. See help(type(self)) for accurate signature.

exception asyncutils.exceptions.WrongPasswordType[T, R: type](
queue: asyncutils._internal.prots.QProtBase[Any, Any] | None,
pwd: T,
wrong_type: type[T],
correct_type: R,
/,
)

Bases: PasswordError[T], TypeError

Raised when the password provided to the get or put methods of a password-protected queue is of the incorrect type.

Initialize self. See help(type(self)) for accurate signature.

property correct_type: R | None

The correct password type associated with the exception. May be None if the wrong password type has been garbage collected, indicating its instances, and thus the password, and by extension the queue itself, have been destroyed.

property wrong_type: type[T] | None

The wrong password type associated with the exception. May be None if the wrong password type has been garbage collected.

class asyncutils.exceptions.IgnoreErrors(
/,
*exc: asyncutils._internal.prots.ExcType,
exclude: collections.abc.Iterable[asyncutils._internal.prots.ExcType] = ...,
)

Context manager to suppress errors of the specified types and exit once they occur; works in both sync and async. More customizable than contextlib.suppress(), because some exception classes can be excluded from the suppression.

Suppress the exception classes specified by the positional arguments within the context, and consume the iterable exclude to build up but. All overlap is discarded.

async __aenter__() Self

Async context support.

async __aexit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) bool
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) Literal[False]

Async context support.

__enter__() Self

Start suppressing the exceptions with types in exc, except those in but, and return the context manager instance.

__exit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) bool
__exit__(exc_typ: None, exc_val: None, exc_tb: None, /) Literal[False]

Stop suppressing the specified exceptions.

combined(
*others: Self | asyncutils._internal.prots.ExcType | collections.abc.Iterable[Self] | collections.abc.Iterable[asyncutils._internal.prots.ExcType],
) Self

Return a combined IgnoreErrors instance that ignores all the error types from itself and the others and respects their exclusions.

excluding(*others: asyncutils._internal.prots.ExcType) Self

Return a new IgnoreErrors instance that ignores the error types from itself except those from the others.

property but: tuple[asyncutils._internal.prots.ExcType, Ellipsis]

The subclasses of exception types in exc that are not ignored.

property exc: tuple[asyncutils._internal.prots.ExcType, Ellipsis]

The exception types that are ignored.

class asyncutils.exceptions.WarningToError(/, *types: type[Warning])

Context manager to convert specific warnings to errors; works in both sync and async.

Positional arguments represent warning types to be raised as errors if they are to occur within the context.

async __aenter__() None

Async context support.

async __aexit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Async context support.

__enter__() Self

Note that an error is to be raised once one of the warning types is encountered within the context and return the context manager instance.

__exit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
__exit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Stop raising errors for the warning types specified.

asyncutils.exceptions.exception_occurred(instance: object, /) TypeIs[asyncutils._internal.prots.ExceptionWrapper]

Whether the object is actually a special proxy to an exception.

asyncutils.exceptions.potent_derive(
group: BaseExceptionGroup,
/,
*more: BaseException,
ordered: bool = ...,
predicate: collections.abc.Callable[[BaseException], bool] = ...,
raise_critical: bool = ...,
keep: asyncutils._internal.prots.CanExcept = ...,
filter_out: asyncutils._internal.prots.CanExcept = ...,
ack1: collections.abc.Callable[[BaseException], object] | None = ...,
ack2: collections.abc.Callable[[BaseException], object] | None = ...,
ack3: collections.abc.Callable[[BaseException], object] | None = ...,
notes: collections.abc.Iterable[str] | None = ...,
) BaseExceptionGroup
asyncutils.exceptions.potent_derive(
exc: asyncutils._internal.prots.NonGroupExc,
/,
*more: BaseException,
message: str,
ordered: bool = ...,
predicate: collections.abc.Callable[[BaseException], bool] = ...,
raise_critical: bool = ...,
keep: asyncutils._internal.prots.CanExcept = ...,
filter_out: asyncutils._internal.prots.CanExcept = ...,
ack1: collections.abc.Callable[[BaseException], object] | None = ...,
ack2: collections.abc.Callable[[BaseException], object] | None = ...,
ack3: collections.abc.Callable[[BaseException], object] | None = ...,
notes: collections.abc.Iterable[str] | None = ...,
traceback: types.TracebackType | None = ...,
context: BaseException,
cause: None = ...,
suppress: bool = ...,
) BaseExceptionGroup
asyncutils.exceptions.potent_derive(
exc: asyncutils._internal.prots.NonGroupExc,
/,
*more: BaseException,
message: str,
ordered: bool = ...,
predicate: collections.abc.Callable[[BaseException], bool] = ...,
raise_critical: bool = ...,
keep: asyncutils._internal.prots.CanExcept = ...,
filter_out: asyncutils._internal.prots.CanExcept = ...,
ack1: collections.abc.Callable[[BaseException], object] | None = ...,
ack2: collections.abc.Callable[[BaseException], object] | None = ...,
ack3: collections.abc.Callable[[BaseException], object] | None = ...,
notes: collections.abc.Iterable[str] | None = ...,
traceback: types.TracebackType | None = ...,
context: None = ...,
cause: BaseException,
suppress: bool = ...,
) BaseExceptionGroup
asyncutils.exceptions.potent_derive(
exc: asyncutils._internal.prots.NonGroupExc,
/,
*more: BaseException,
message: str,
ordered: bool = ...,
predicate: collections.abc.Callable[[BaseException], bool] = ...,
raise_critical: bool = ...,
keep: asyncutils._internal.prots.CanExcept = ...,
filter_out: asyncutils._internal.prots.CanExcept = ...,
ack1: collections.abc.Callable[[BaseException], object] | None = ...,
ack2: collections.abc.Callable[[BaseException], object] | None = ...,
ack3: collections.abc.Callable[[BaseException], object] | None = ...,
notes: collections.abc.Iterable[str] | None = ...,
traceback: types.TracebackType | None = ...,
context: None = ...,
cause: None = ...,
suppress: bool = ...,
) BaseExceptionGroup
Return an instance of BaseExceptionGroup, applying the specified filtering and combining the exceptions from other groups, flattening when necessary.
ordered, whether to emit the exceptions in original order, defaults to False, because that is more efficient.
The intersection of filter_out and keep, which are exception types (or tuples thereof), should be non-empty; they are redundant otherwise.
The acknowledgement parameters ack1, ack2 and ack3 are called on exceptions in the above intersection, exceptions that don’t pass the predicate and exceptions that are not in keep respectively.
They must be callables that return fast (e.g. collecting into a list) to avoid slowing down the function.
If raise_critical is True, exit early once a critical exception (type of which is a member of CRITICAL) is encountered and propagate it.
notes is attached to the group using add_note().
suppress, context, cause and traceback are used to add metadata to the result group; see prepare_exception(). They only take effect, however, when the first argument is not a group.
asyncutils.exceptions.prepare_exception[T: BaseException](
exc: T,
/,
*,
traceback: types.TracebackType | None = ...,
cause: BaseException | None = ...,
context: BaseException | None = ...,
suppress: bool = ...,
notes: collections.abc.Iterable[str] = ...,
) T
Attach some info to the exception exc and return it.
notes is an iterable of strings that are added to the exception using add_note(). If a single string, it is treated as one note; to avoid this for some reason, convert the string to a tuple beforehand.
traceback corresponds to the attribute __traceback__, cause to __cause__,
context to __context__ and suppress to __suppress_context__.
asyncutils.exceptions.raise_exc(
exc_typ: asyncutils._internal.prots.ExcType,
/,
*args: object,
traceback: types.TracebackType | None = ...,
cause: BaseException | None = ...,
context: BaseException | None = ...,
suppress: bool = ...,
notes: collections.abc.Iterable[str] = ...,
**kwargs: object,
) NoReturn
asyncutils.exceptions.raise_exc(
exc_val: BaseException,
/,
*,
traceback: types.TracebackType | None = ...,
cause: BaseException | None = ...,
context: BaseException | None = ...,
suppress: bool = ...,
notes: collections.abc.Iterable[str] = ...,
) NoReturn

Programmatically raise an exception. The variadic args and kwargs are passed to the constructor of exc_typ in the first overload, and the remaining arguments are as in potent_derive().

asyncutils.exceptions.unnest(
group: BaseException,
/,
*more: BaseException,
raise_critical: bool = ...,
keep: asyncutils._internal.prots.CanExcept = ...,
filter_out: asyncutils._internal.prots.CanExcept = ...,
predicate: collections.abc.Callable[[BaseException], bool] = ...,
ack1: collections.abc.Callable[[BaseException], object] | None = ...,
ack2: collections.abc.Callable[[BaseException], object] | None = ...,
ack3: collections.abc.Callable[[BaseException], object] | None = ...,
) types.GeneratorType[BaseException, BaseException]
Flatten exceptions that may be nested in BaseExceptionGroup’s, with priority for those just sent in.
Keyword arguments are as in potent_derive().

Tip

Use this only when you must preserve the order, and the faster unnest_reverse() otherwise.

asyncutils.exceptions.unnest_reverse(
group: BaseException,
/,
*more: BaseException,
raise_critical: bool = ...,
keep: asyncutils._internal.prots.CanExcept = ...,
filter_out: asyncutils._internal.prots.CanExcept = ...,
predicate: collections.abc.Callable[[BaseException], bool] = ...,
ack1: collections.abc.Callable[[BaseException], object] | None = ...,
ack2: collections.abc.Callable[[BaseException], object] | None = ...,
ack3: collections.abc.Callable[[BaseException], object] | None = ...,
) types.GeneratorType[BaseException, BaseException]

Basically the above but in reverse order, with rare edge cases. More memory- and time-efficient than unnest.

asyncutils.exceptions.unwrap_exc(instance: asyncutils._internal.prots.ExceptionWrapper, /) BaseException

Recover the exception wrapped by wrap_exc(). This function does not raise the exception because it may sometimes be useful to have the exception object itself, for example when setting it on a Future.

asyncutils.exceptions.wrap_exc(exc: BaseException, /) asyncutils._internal.prots.ExceptionWrapper

Wrap an exception in a special proxy wrapper, such that exception_occurred(wrapper) returns True.

asyncutils.exceptions.CRITICAL: Final[tuple[type[SystemExit], type[SystemError], type[KeyboardInterrupt]]]

The tuple (SystemExit, SystemError, KeyboardInterrupt), representing exceptions that should be allowed to propagate under most error handling mechanisms.

asyncutils.exceptions.ignore_all: Final[IgnoreErrors]

Instance of IgnoreErrors that ignores all errors; that is, IgnoreErrors(BaseException). Use with caution!

asyncutils.exceptions.ignore_noncritical: Final[IgnoreErrors]

Instance of IgnoreErrors that ignores all errors besides SystemExit, SystemError and KeyboardInterrupt. Equivalent to ignore_all.excluding(*CRITICAL).

asyncutils.exceptions.ignore_stop_async_iteration: Final[IgnoreErrors]

Instance of IgnoreErrors that ignores StopAsyncIteration. Equivalent to IgnoreErrors(StopAsyncIteration).

asyncutils.exceptions.ignore_stop_iteration: Final[IgnoreErrors]

Instance of IgnoreErrors that ignores StopIteration. Equivalent to IgnoreErrors(StopIteration).

asyncutils.exceptions.ignore_typeerrs: Final[IgnoreErrors]

Instance of IgnoreErrors that ignores TypeError. Equivalent to IgnoreErrors(TypeError).

asyncutils.exceptions.ignore_typical: Final[IgnoreErrors]

Instance of IgnoreErrors that ignores Exception and subclasses thereof. Equivalent to IgnoreErrors().

asyncutils.exceptions.ignore_valerrs: Final[IgnoreErrors]

Instance of IgnoreErrors that ignores ValueError. Equivalent to IgnoreErrors(ValueError).

asyncutils.exceptions.ignore_warnings: Final[IgnoreErrors]

Instance of IgnoreErrors that ignores Warning. Equivalent to IgnoreErrors(Warning).

asyncutils.func

Higher-order functions with asynchronous APIs, containing utilities to retry, time, throttle, run functions periodically and more.

Classes

RateLimited

The rate limiter pattern as a decorator (factory). See AdvancedRateLimit for the async context manager version.

Functions

acompose(→ collections.abc.Callable[Ellipsis, Any])

Compose multiple functions. If the result of a function is a coroutine, await it before passing it to the next. Begin from the rightmost function, which can take variadic parameters, and then pipe its return value through as a single argument.

areduce(…)

Async version of functools.reduce() that takes an async function and possibly async iterable. If the function is sync or the return value is not meant to be awaited, specify await_=False.

benchmark(→ asyncutils._internal.prots.BenchmarkResult)

debounce(→ asyncutils._internal.prots.DecoratorFactoryRV)

Return a decorator that debounces the wrapped function, such that it is only called after it has not been called for wait seconds.

every(…)

everymethod(…)

every(), but applying to methods. stop_when_getter, if passed, should take self and returns a suitable future stop_when. Other parameters are as in every().

iterf(...)

Return a decorator that applies the decorated function n times to its argument.

measure(→ tuple[T, ty_extensions.JustFloat])

Return a tuple (result, elapsed), where result is the awaited return value of the function and elapsed is the time taken.

measure2(→ ty_extensions.JustFloat)

Return the time used to execute the function, discarding the return value.

retry(→ asyncutils._internal.prots.DecoratorFactoryRV)

star(...)

Convert a function taking variadic parameters and returning an awaitable into a coroutine function taking two arguments: an iterable of positional arguments and a mapping of keyword arguments.

throttle(→ asyncutils._internal.prots.DecoratorFactoryRV)

Return a decorator that throttles the wrapped function, such that it can only be called once every lim seconds, as determined by timer.

timer(→ collections.abc.Callable[P, ...)

unstar(→ collections.abc.Callable[Ellipsis, ...)

Undo the effect of star().

Module Contents
class asyncutils.func.RateLimited[T, **P]

The rate limiter pattern as a decorator (factory). See AdvancedRateLimit for the async context manager version.

Limit the rate of calls of a function f, such that only calls calls within period seconds, as determined by timer, are allowed.

async __call__(*a: P.args, **k: P.kwargs) T
asyncutils.func.acompose(
*functions: collections.abc.Callable[Ellipsis, Any],
wrap_last: bool = ...,
) collections.abc.Callable[Ellipsis, Any]

Compose multiple functions. If the result of a function is a coroutine, await it before passing it to the next. Begin from the rightmost function, which can take variadic parameters, and then pipe its return value through as a single argument.

async asyncutils.func.areduce[T](
f: collections.abc.Callable[Ellipsis, object],
it: asyncutils._internal.prots.SupportsIteration[Never],
initial: T,
*,
await_: bool = ...,
) T
async asyncutils.func.areduce(
f: collections.abc.Callable[[T, R], collections.abc.Awaitable[T]],
it: asyncutils._internal.prots.SupportsIteration[R],
initial: T = ...,
*,
await_: Literal[True] = ...,
) T
async asyncutils.func.areduce(
f: collections.abc.Callable[[T, R], T],
it: asyncutils._internal.prots.SupportsIteration[R],
initial: T = ...,
*,
await_: Literal[False],
) T

Async version of functools.reduce() that takes an async function and possibly async iterable. If the function is sync or the return value is not meant to be awaited, specify await_=False.

async asyncutils.func.benchmark(
f: collections.abc.Callable[[], collections.abc.Awaitable[Any]],
/,
times: int = ...,
warmup: int = ...,
*,
sequential: bool = ...,
) asyncutils._internal.prots.BenchmarkResult
  • f: the function to benchmark, which should take no arguments and return an awaitable

  • times (default BENCHMARK_DEFAULT_TIMES): the number of times the function should be run

  • warmup (default BENCHMARK_DEFAULT_WARMUP): the number of warmup rounds to call the function for; not included in the benchmark results

  • sequential (default BENCHMARK_DEFAULT_SEQUENTIAL): determines whether the function calls are made sequentially or gathered at once. For example, for functions requiring a mutex to be acquired or with other rate-limiting policies in place, you should explicitly pass sequential=True.

This function should only be used in very simple cases, because we recognize the inherent difficulty and abundance of noise in testing IO-bound code, and this library alone is by no means designed to solve that issue.

asyncutils.func.debounce(wait: float) asyncutils._internal.prots.DecoratorFactoryRV

Return a decorator that debounces the wrapped function, such that it is only called after it has not been called for wait seconds.

asyncutils.func.every(
interval: float,
/,
*,
count_f: bool = ...,
verbose: bool = ...,
stop_on_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
wait_first: bool = ...,
max_iterations: int | None = ...,
timer: asyncutils._internal.prots.Timer = ...,
supplied_args: collections.abc.Iterable[Any] = ...,
supplied_kwargs: collections.abc.Mapping[str, Any] = ...,
) asyncutils._internal.prots.EveryRV[Any]
asyncutils.func.every(
interval: float,
/,
*,
stop_when: asyncio.Future[T],
count_f: bool = ...,
verbose: bool = ...,
stop_on_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
wait_first: bool = ...,
max_iterations: int | None = ...,
timer: asyncutils._internal.prots.Timer = ...,
supplied_args: collections.abc.Iterable[Any] = ...,
supplied_kwargs: collections.abc.Mapping[str, Any] = ...,
) asyncutils._internal.prots.EveryRV[T]
asyncutils.func.every(
interval: float,
/,
*,
count_f: bool = ...,
verbose: bool = ...,
stop_on_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
wait_first: bool = ...,
max_iterations: int | None = ...,
timer: asyncutils._internal.prots.Timer = ...,
supplied_args: collections.abc.Iterable[Any] = ...,
supplied_kwargs: collections.abc.Mapping[str, Any] = ...,
default: T,
) asyncutils._internal.prots.EveryRV[T]
asyncutils.func.every(
interval: float,
/,
*,
stop_when: asyncio.Future[T],
count_f: bool = ...,
verbose: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
stop_on_exc: bool = ...,
wait_first: bool = ...,
max_iterations: int | None = ...,
timer: asyncutils._internal.prots.Timer = ...,
supplied_args: collections.abc.Iterable[Any] = ...,
supplied_kwargs: collections.abc.Mapping[str, Any] = ...,
default: T,
) asyncutils._internal.prots.EveryRV[T]
Return a decorator that repeats a function regularly. Useful for periodic monitoring tasks.
The resultant function will run every interval seconds, as determined by timer, at most max_iterations times.
If count_f is True, this time includes the execution time of the function.
If wait_first is True, sleep for interval seconds before the first execution.
If stop_on_exc is True, the function returns once the decorated function throws any exception or stop_when is cancelled.
verbose makes the function treat exceptions more severely output-wise.
Once the result of stop_when is set, the function returns that result, which should be None or the same type as the return type of the decorated function after awaiting. However, the task is guaranteed to be run at least once.
When using the supplied_args and supplied_kwargs parameters, maintain a reference to them so that you can edit the parameters fed to the function on the fly.
Finally, the function returns default or None if it was not passed, unless stop_on_exc is True or default is RAISE, in which case MaxIterationsError is thrown.
asyncutils.func.everymethod(
interval: float,
/,
*,
count_f: bool = ...,
verbose: bool = ...,
stop_on_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
wait_first: bool = ...,
max_iterations: int | None = ...,
timer: asyncutils._internal.prots.Timer = ...,
supplied_args: collections.abc.Iterable[Any] = ...,
supplied_kwargs: collections.abc.Mapping[str, Any] = ...,
) asyncutils._internal.prots.EveryMethodRV[Any, Any]
asyncutils.func.everymethod(
interval: float,
/,
*,
stop_when_getter: collections.abc.Callable[[T], asyncio.Future[R]],
count_f: bool = ...,
verbose: bool = ...,
stop_on_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
wait_first: bool = ...,
max_iterations: int | None = ...,
timer: asyncutils._internal.prots.Timer = ...,
supplied_args: collections.abc.Iterable[Any] = ...,
supplied_kwargs: collections.abc.Mapping[str, Any] = ...,
) asyncutils._internal.prots.EveryMethodRV[R, T]
asyncutils.func.everymethod(
interval: float,
/,
*,
count_f: bool = ...,
verbose: bool = ...,
stop_on_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
wait_first: bool = ...,
max_iterations: int | None = ...,
timer: asyncutils._internal.prots.Timer = ...,
supplied_args: collections.abc.Iterable[Any] = ...,
supplied_kwargs: collections.abc.Mapping[str, Any] = ...,
default: T,
) asyncutils._internal.prots.EveryMethodRV[T, Any]
asyncutils.func.everymethod(
interval: float,
/,
*,
stop_when_getter: collections.abc.Callable[[T], asyncio.Future[R]],
count_f: bool = ...,
verbose: bool = ...,
stop_on_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
wait_first: bool = ...,
max_iterations: int | None = ...,
timer: asyncutils._internal.prots.Timer = ...,
supplied_args: collections.abc.Iterable[Any] = ...,
supplied_kwargs: collections.abc.Mapping[str, Any] = ...,
default: R,
) asyncutils._internal.prots.EveryMethodRV[R, T]

every(), but applying to methods. stop_when_getter, if passed, should take self and returns a suitable future stop_when. Other parameters are as in every().

asyncutils.func.iterf[
T,
](
n: int,
/,
) collections.abc.Callable[[collections.abc.Callable[[T], collections.abc.Awaitable[T]]], collections.abc.Callable[[T], types.CoroutineType[Any, Any, T]]]

Return a decorator that applies the decorated function n times to its argument.

async asyncutils.func.measure[T](
f: collections.abc.Callable[[], collections.abc.Awaitable[T]],
/,
*,
timer: asyncutils._internal.prots.Timer = ...,
) tuple[T, ty_extensions.JustFloat]

Return a tuple (result, elapsed), where result is the awaited return value of the function and elapsed is the time taken.

async asyncutils.func.measure2[T](
f: collections.abc.Callable[[], collections.abc.Awaitable[T]],
/,
*,
timer: asyncutils._internal.prots.Timer = ...,
) ty_extensions.JustFloat

Return the time used to execute the function, discarding the return value.

asyncutils.func.retry(
tries: int = ...,
delay: float = ...,
*,
max_delay: float = ...,
backoff: float = ...,
jitter: float = ...,
exc: asyncutils._internal.prots.CanExcept = ...,
on_retry: collections.abc.Callable[[int, BaseException], Any] = ...,
on_success: collections.abc.Callable[[int, float], Any] = ...,
random: collections.abc.Callable[[], float] = ...,
) asyncutils._internal.prots.DecoratorFactoryRV
Return a decorator that retries the wrapped function with exponential backoff, returning once the function succeeds.
  • If the function does not succeed within tries attempts (default RETRY_DEFAULT_TRIES), the last exception is propagated.

  • backoff (default RETRY_DEFAULT_BACKOFF) is the multiplier applied to the delay (initially delay which defaults to RETRY_DEFAULT_DELAY) after each failed attempt, which can never exceed max_delay (default RETRY_DEFAULT_MAX_DELAY).

  • jitter (default RETRY_DEFAULT_JITTER) is the maximum random jitter added to the delay.

  • exc specifies which exceptions to catch and retry on; if an exception not in exc is raised, it is propagated immediately.

  • on_retry and on_success are callbacks called before each retry and after a successful call, with the attempt number (zero-based) as the first argument and the exception caught or the time taken for the successful call respectively as the second. Thus, on_success is only called once.

asyncutils.func.star[
T,
](
f: collections.abc.Callable[Ellipsis, collections.abc.Awaitable[T]],
/,
) collections.abc.Callable[[collections.abc.Iterable[Any], collections.abc.Mapping[str, Any]], types.CoroutineType[Any, Any, T]]

Convert a function taking variadic parameters and returning an awaitable into a coroutine function taking two arguments: an iterable of positional arguments and a mapping of keyword arguments.

asyncutils.func.throttle(lim: float, timer: asyncutils._internal.prots.Timer = ...) asyncutils._internal.prots.DecoratorFactoryRV

Return a decorator that throttles the wrapped function, such that it can only be called once every lim seconds, as determined by timer.

asyncutils.func.timer[
T,
**P,
](
f: collections.abc.Callable[P, collections.abc.Awaitable[T]],
/,
*,
precision: int = ...,
expected: asyncutils._internal.prots.CanExcept = ...,
should_log: bool = ...,
timer: asyncutils._internal.prots.Timer = ...,
ns: bool = ...,
) collections.abc.Callable[P, types.CoroutineType[Any, Any, tuple[T | asyncutils._internal.prots.ExceptionWrapper, float]]]
Convert the function that returns an awaitable object into an async function that returns a tuple (res_or_exc, elapsed).
  • timer (default time.perf_counter()) is used to count elapsed, the time required to execute the function.

  • res_or_exc is the awaited result of the wrapped function, or the exception thrown as wrapped by wrap_exc().

  • precision (default TIMER_DEFAULT_PRECISION) is the number of digits after the decimal point to keep in the time in logging

  • If ns=True is passed, elapsed is in nanoseconds.

  • Any exception the wrapped function emits whose type is not in expected is propagated directly.

  • If should_log=False is passed, progress of the function execution (start and end) is not logged.

asyncutils.func.unstar[T](
f: collections.abc.Callable[[collections.abc.Iterable[Any], collections.abc.Mapping[str, Any]], collections.abc.Awaitable[T]],
/,
) collections.abc.Callable[Ellipsis, types.CoroutineType[Any, Any, T]]

Undo the effect of star().

asyncutils.futures

Various implementations of future and task classes, eager, time-aware and supporting asynchronous and no-argument callbacks.

Classes

AsyncCallbacksFuture

A subclass of Future that supports calling asynchronous callbacks and callbacks with no arguments on completion.

AsyncCallbacksTask

Self-explanatory.

TimeAwareAsyncCallbacksFuture

A subclass of AsyncCallbacksFuture that can be compared to other TimeAwareAsyncCallbacksFuture's based on the time they were created.

TimeAwareAsyncCallbacksTask

A subclass of AsyncCallbacksTask that can be compared to other TimeAwareAsyncCallbacksTask's based on the time they were created.

TimeAwareFuture

A subclass of Future that can be compared to other TimeAwareFuture's based on the time they were created.

TimeAwareTask

A subclass of Task that can be compared to other TimeAwareTask's based on the time they were created.

TimeAwareUniqueCallbacksFuture

A subclass of UniqueCallbacksFuture that can be compared to other TimeAwareUniqueCallbacksFuture's based on the time they were created.

TimeAwareUniqueCallbacksTask

A subclass of UniqueCallbacksTask that can be compared to other TimeAwareUniqueCallbacksTask's based on the time they were created.

UniqueCallbacksFuture

Like AsyncCallbacksFuture, but disallow the same callback from being added twice. Removal is faster and more intuitive to use.

UniqueCallbacksTask

Self-explanatory.

Module Contents
class asyncutils.futures.AsyncCallbacksFuture[T](*, loop: asyncio.AbstractEventLoop | None = ...)

Bases: asyncio.Future[T]

A subclass of Future that supports calling asynchronous callbacks and callbacks with no arguments on completion.

Note

To hook into the callbacks mechanism, subclassing the C-accelerated implementation of Future is impossible; i.e., using many of them, for example when implementing a queue, may be slower.

add_async_callback(
fn: collections.abc.Callable[[Self], collections.abc.Awaitable[object]],
/,
*,
context: contextvars.Context | None = ...,
) None

Add an asynchronous callback to be called when the future is done. The callback will be passed the future as an argument.

add_noargs_async_callback(
fn: collections.abc.Callable[[], collections.abc.Awaitable[object]],
/,
*,
context: contextvars.Context | None = ...,
) None

Add an asynchronous callback with no arguments to be called when the future is done.

add_noargs_callback(fn: collections.abc.Callable[[], object], /, *, context: contextvars.Context | None = ...) None

Add a callback with no arguments to be called when the future is done.

remove_async_callback(fn: collections.abc.Callable[[Self], collections.abc.Awaitable[object]], /) int

Remove an asynchronous callback. Returns the number of callbacks removed.

remove_done_callback(fn: collections.abc.Callable[[Self], object], /) int

Remove a callback. Returns the number of callbacks removed.

remove_noargs_async_callback(fn: collections.abc.Callable[[], collections.abc.Awaitable[object]], /) int

Remove an asynchronous callback with no arguments. Returns the number of callbacks removed.

remove_noargs_callback(fn: collections.abc.Callable[[], object], /) int

Remove a callback with no arguments. Returns the number of callbacks removed.

class asyncutils.futures.AsyncCallbacksTask[T](*, loop: asyncio.AbstractEventLoop | None = ...)

Bases: asyncio.Task[T], AsyncCallbacksFuture[T]

Self-explanatory.

class asyncutils.futures.TimeAwareAsyncCallbacksFuture[T](*, loop: asyncio.AbstractEventLoop | None = ...)

Bases: TimeAwareFuture[T], AsyncCallbacksFuture[T]

A subclass of AsyncCallbacksFuture that can be compared to other TimeAwareAsyncCallbacksFuture’s based on the time they were created.

class asyncutils.futures.TimeAwareAsyncCallbacksTask[T](*, loop: asyncio.AbstractEventLoop | None = ...)

Bases: TimeAwareTask[T], AsyncCallbacksTask[T]

A subclass of AsyncCallbacksTask that can be compared to other TimeAwareAsyncCallbacksTask’s based on the time they were created.

class asyncutils.futures.TimeAwareFuture[T]

Bases: asyncio.Future[T]

A subclass of Future that can be compared to other TimeAwareFuture’s based on the time they were created.

__lt__(other: TimeAwareFuture[Any] | TimeAwareTask[Any], /) bool
class asyncutils.futures.TimeAwareTask[T]

Bases: asyncio.Task[T]

A subclass of Task that can be compared to other TimeAwareTask’s based on the time they were created.

__lt__(other: TimeAwareFuture[Any] | TimeAwareTask[Any], /) bool
class asyncutils.futures.TimeAwareUniqueCallbacksFuture[T](*, loop: asyncio.AbstractEventLoop | None = ...)

Bases: TimeAwareFuture[T], UniqueCallbacksFuture[T]

A subclass of UniqueCallbacksFuture that can be compared to other TimeAwareUniqueCallbacksFuture’s based on the time they were created.

class asyncutils.futures.TimeAwareUniqueCallbacksTask[T](*, loop: asyncio.AbstractEventLoop | None = ...)

Bases: TimeAwareTask[T], UniqueCallbacksTask[T]

A subclass of UniqueCallbacksTask that can be compared to other TimeAwareUniqueCallbacksTask’s based on the time they were created.

class asyncutils.futures.UniqueCallbacksFuture[T](*, loop: asyncio.AbstractEventLoop | None = ...)

Bases: asyncio.Future[T]

Like AsyncCallbacksFuture, but disallow the same callback from being added twice. Removal is faster and more intuitive to use.

add_async_callback(
fn: collections.abc.Callable[[Self], collections.abc.Awaitable[object]],
/,
*,
context: contextvars.Context | None = ...,
) None

Add an asynchronous callback to be called when the future is done. The callback will be passed the future as an argument.

add_done_callback(fn: collections.abc.Callable[[Self], object], /, *, context: contextvars.Context | None = ...) None

Add a callback to be called when the future is done. The callback will be passed the future as an argument.

add_noargs_async_callback(
fn: collections.abc.Callable[[], collections.abc.Awaitable[object]],
/,
*,
context: contextvars.Context | None = ...,
) None

Add an asynchronous callback with no arguments to be called when the future is done.

add_noargs_callback(fn: collections.abc.Callable[[], object], /, *, context: contextvars.Context | None = ...) None

Add a callback with no arguments to be called when the future is done.

remove_async_callback(fn: collections.abc.Callable[[Self], collections.abc.Awaitable[object]], /) Literal[0, 1]

Remove an asynchronous callback. Returns the number of callbacks removed.

remove_done_callback(fn: collections.abc.Callable[[Self], object], /) Literal[0, 1]

Remove a callback. Returns the number of callbacks removed.

remove_noargs_async_callback(fn: collections.abc.Callable[[], collections.abc.Awaitable[object]], /) Literal[0, 1]

Remove an asynchronous callback with no arguments. Returns the number of callbacks removed.

remove_noargs_callback(fn: collections.abc.Callable[[], object], /) Literal[0, 1]

Remove a callback with no arguments. Returns the number of callbacks removed.

class asyncutils.futures.UniqueCallbacksTask[T](*, loop: asyncio.AbstractEventLoop | None = ...)

Bases: asyncio.Task[T], UniqueCallbacksFuture[T]

Self-explanatory.

asyncutils.iotools
Provides asynchronous file-like interfaces to the following: coupled reader and writer, write-one-end-and-read-the-other pipes, and memory maps.
Does not depend on aiofiles or any such library.
Executors of type as determined by the module configuration are used.
This library is not designed to do I/O operations, and the functionality in this submodule is far from comprehensive.
See aiostream or similar for that.
Attributes

stdcoup

Instance of AsyncReadWriteCouple wrapping standard input and output.

Classes

AsyncReadWriteCouple

MemoryMappedIOManager

An asynchronous object-oriented manager interface to memory-mapped I/O, that optimizes batch operations using an event loop.

Functions

ainput(→ str)

Asynchronously write prompt to standard output and read a line from standard input, returning it without the trailing newline. If assert_tty is True, raise OSError if standard input is not a TTY (You need only pass this the first time you call the function).

double_ended_binary_pipe(...)

double_ended_text_pipe(), but opens the pipes in binary mode.

double_ended_text_pipe(...)

Module Contents
class asyncutils.iotools.AsyncReadWriteCouple[T: (str, bytes), R: (str, bytes)](
reader: asyncutils._internal.prots.Reader[T],
writer: asyncutils._internal.prots.Writer[R],
/,
executor: asyncutils.config.Executor | None = ...,
*,
find_attr_on_writer_first: bool = ...,
)

Bases: asyncutils.mixins.LoopContextMixin

An asynchronous file-like interface to a readable and writable object.
Delegates its methods to the underlying reader and writer, but makes them non-blocking by running in an executor.
Preferably, the executor should be a thread pool, but that is ultimately determined by the library configuration.

Warning

This class is not designed to wrap asyncio streams because their methods are different and already async.

See also

io.BufferedRWPair

The standard library synchronous equivalent. Some of its methods may not be present here.

Initialize the couple with the given reader, writer and optionally a PEP 3148 executor to call the file methods in, after checking that the reader is readable and the writer is writable.

async __cleanup__() None
__getattr__(name: str, /) Any

Search for the attribute on the writer first if find_attr_on_writer_first=True was passed and the reader otherwise.

async aclose() None

Close the reader and writer asynchronously and shut down the underlying executor. It is safe to close a file multiple times, but no other methods should be called after closing.

fileno() NoReturn

Raise OSError with errno EBADF.

async flush() None

Asynchronously flush the writer.

isatty() NoReturn

Raise OSError with errno ENOTSUP.

async read(n: int = ..., /) T

Read n characters from the reader.

async read1(n: int = ..., /) T

Call the read1() method on the reader.

readable() Literal[True]

Return True, because prior verification has been done that the reader is readable, and that is assumed not to be invalidated.

async readall() T

Read all characters from the reader until EOF. If the readall() method is not present, call read() with no arguments without handling the non-blocking case.

async readinto(b: collections.abc.Buffer, /) int
Read into the writable bytes-like object b from the reader, returning the number of bytes read.
Calls the readinto() method of the reader if it exists and falls back to the read() method.
The case where the underlying implementation of read() returns None or raises BlockingIOError is not considered.
async readinto1(b: collections.abc.Buffer, /) int

Call the readinto1() method on the reader. There is no fallback implementation.

async readline(limit: int = ..., /) T

Read a line, of length at most limit, from the reader.

async readlines(hint: int = ..., /) list[T]

Collect lines of the file into a list until at least hint characters are read (if available), and a line boundary is encountered.

seek(offset: int, whence: int = ..., /) NoReturn

Raise OSError with errno ESPIPE.

seekable() Literal[False]

Return False since the couple itself is not seekable, but the reader and writer may be..

tell() NoReturn

Raise OSError with errno ESPIPE.

async truncate(size: int | None = ..., /) int

Truncate the file at size (or the current position if not passed), and return the new file size.

writable() Literal[True]

Return True, because prior verification has been done that the writer is writable, and that is assumed not to be invalidated.

async write(s: R, /) int

Write s into the writer, returning the number of characters written.

async writelines(lines: collections.abc.Iterable[R], /) None

Write the lines from the iterable into the writer without adding newline as separators.

property closed: bool

Whether both the reader and writer have been closed.

property executor: asyncutils.config.Executor

The underlying executor.

property reader: asyncutils._internal.prots.Reader[T]

The underlying reader.

property writer: asyncutils._internal.prots.Writer[R]

The underlying writer.

class asyncutils.iotools.MemoryMappedIOManager(executor: asyncutils.config.Executor | None = ...)

Bases: asyncutils.mixins.LoopContextMixin

An asynchronous object-oriented manager interface to memory-mapped I/O, that optimizes batch operations using an event loop.

Tip

You will probably only ever need one instance of this.

Initialize the manager with the executor to be used for its operations.

async __cleanup__() None
__del__() None
async approx_memory_usage() int

Compute the approximate memory used by the currently open memory maps in bytes.

async bulk_checksum[T: asyncutils._internal.prots.Openable](paths: collections.abc.Iterable[T], alg: asyncutils._internal.prots.HashAlgorithm = ...) dict[T, str]

Compute checksums from the files at paths using the specified algorithm, defaulting to MEMORY_MAPPED_IO_MANAGER_DEFAULT_CHECKSUM_ALG. The same remarks from checksum() apply here.

async bulk_copy(
pairs: collections.abc.Iterable[tuple[asyncutils._internal.prots.Openable, asyncutils._internal.prots.Openable]],
) None

Copy the contents of each file in the first position of the tuples in pairs into the file in the second position asynchronously. If you have a dictionary, pass in its items view.

async bulk_read[T: asyncutils._internal.prots.Openable](file_offsets: collections.abc.Mapping[T, collections.abc.Iterable[tuple[int, int]]]) dict[T, list[bytes]]

Read from each file at their corresponding offsets as specified by the value in the file_offsets mapping, which should be an iterable of tuples (offset, size) or None if the whole file is to be read.

async bulk_resize(sizes: collections.abc.Mapping[asyncutils._internal.prots.Openable, int]) None

Resize each file at the keys of sizes to the corresponding value asynchronously.

async bulk_write(
file_data: collections.abc.Mapping[asyncutils._internal.prots.Openable, collections.abc.Iterable[tuple[bytes, int]]],
) None

Write into each file at their corresponding offsets as specified by the value in the file_data mapping, which should be an iterable of tuples (data, offset).

async checksum(path: asyncutils._internal.prots.Openable, alg: asyncutils._internal.prots.HashAlgorithm = ...) str
Compute a checksum from the file at path using the specified algorithm (default MEMORY_MAPPED_IO_MANAGER_DEFAULT_CHECKSUM_ALG).
usedforsecurity=False is passed to the hashlib.new() constructor to bypass FIPS restrictions, such that broken algorithms like MD5 are always allowed if explicitly requested, seeing as though they are fast and enough to prevent accidental file corruption in simple cases.

Caution

If executing cryptographic checksums, use the factory default BLAKE2s (32-bit) or BLAKE2b (64-bit), SHA256, or similar.

Danger

Calling without the alg parameter may cause a faulty algorithm to be chosen if the value in the current context dictates so.

See also

hashlib.algorithms_available

For the set of supported algorithms on your system and installation.

The relevant FIPS specification

For the security requirements of the algorithms.

The Wikipedia article

For basic information pertaining to checksums and their use cases.

async compact_files(paths: collections.abc.Iterable[asyncutils._internal.prots.Openable]) None

Reduce the size of each file at paths by truncating the trailing null bytes asynchronously.

async copy_file(
src: asyncutils._internal.prots.Openable,
dest: asyncutils._internal.prots.Openable,
*,
exclusive: bool = ...,
flush: bool = ...,
) None

Copy the contents of the file at src into that at dest asynchronously and flush it if flush is True. Uses open() and create() internally.

create(
path: asyncutils._internal.prots.Openable,
init_size: int = ...,
*,
exclusive: bool = ...,
) asyncutils._internal.prots.OpenRV

Open a file at path for memory-mapped writing and reading on entry and close it on exit. The file is truncated to the beginning, and must not exist if exclusive is True (the default behaviour).

create_sparse_file(
path: asyncutils._internal.prots.Openable,
total_size: int,
chunks: collections.abc.Mapping[int, bytes | str],
) asyncutils._internal.prots.OpenRV

Return an async context manager that creates a file of size total_size at path, with chunks mapping offsets to the data to be written there. Data from old chunks is overwritten by that from new ones.

async find_in_files[T: asyncutils._internal.prots.Openable](
pattern: bytes,
paths: collections.abc.Mapping[T, int],
max_per_file: int = ...,
*,
allow_overlapping: bool = ...,
) dict[T, list[int]]

Find all occurrences of pattern in the files at paths, returning a mapping from each file to a list of offsets where the pattern was found.

open(path: asyncutils._internal.prots.Openable, init_size: int = ...) asyncutils._internal.prots.OpenRV

Open a file at path for memory-mapped reading and writing on entry and close it on exit. The file must exist and is not truncated.

prefetch_files(
*paths: asyncutils._internal.prots.Openable,
init_size: int = ...,
) contextlib.AbstractAsyncContextManager[list[asyncutils._internal.prots.MemoryMappedFile], None]

Prefetch existing files at paths for memory-mapped I/O into memory at once, closing them simultaneously on exit.

property currently_open: int

Number of currently open memory maps.

property open_files: asyncutils._internal.prots.OpenFiles

Dictionary mapping tuples of the form (file, mode) to the managed file objects.

property open_maps: weakref.WeakSet[mmap.mmap]

Instance of WeakSet containing the maps managed by this manager.

property open_paths: dict[asyncutils._internal.prots.Openable, Literal['r+b', 'w+b', 'x+b']]

Dictionary mapping file paths as passed to open(), create() or create_sparse_file() to the mode the file was opened with.

async asyncutils.iotools.ainput(prompt: str = ..., assert_tty: bool = ...) str

Asynchronously write prompt to standard output and read a line from standard input, returning it without the trailing newline. If assert_tty is True, raise OSError if standard input is not a TTY (You need only pass this the first time you call the function).

asyncutils.iotools.double_ended_binary_pipe(
*,
pipe_impl: collections.abc.Callable[[], tuple[int, int]] = ...,
) tuple[AsyncReadWriteCouple[bytes, bytes], AsyncReadWriteCouple[bytes, bytes]]

double_ended_text_pipe(), but opens the pipes in binary mode.

asyncutils.iotools.double_ended_text_pipe(
*,
pipe_impl: collections.abc.Callable[[], tuple[int, int]] = ...,
) tuple[AsyncReadWriteCouple[str, str], AsyncReadWriteCouple[str, str]]
Return a tuple of two AsyncReadWriteCouple’s in text mode, such that each can read what the other writes.
Two operating system level pipes are created.
Pass a function that returns a tuple of two integer file descriptors for pipe_impl (default os.pipe()) to customize this behaviour.
asyncutils.iotools.stdcoup: AsyncReadWriteCouple[str, str]

Instance of AsyncReadWriteCouple wrapping standard input and output.

asyncutils.iterclasses

Object-oriented (async) iteration helpers.

Classes

ABucket

Async version of more_itertools.bucket().

AChain

Async version of chain() that takes async or sync iterables.

APeekable

Async version of more_itertools.peekable.

Module Contents
class asyncutils.iterclasses.ABucket[T, R](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], R],
validator: collections.abc.Callable[[R], bool] | None = ...,
)

Bases: asyncutils.mixins.LoopContextMixin

Async version of more_itertools.bucket().

Divide items from the (async) iterable it into child generators according to a key function.

__aiter__() types.AsyncGeneratorType[T]

Yield the keys of all buckets. When this async generator is exhausted, the original iterable is fully consumed. Unlike the sync version, an exhausted bucket has no keys.

__getitem__(key: R, /) types.AsyncGeneratorType[T]

Return an async generator of the items in the original iterable for which the key function gives this key.

async contains(key: R, /) bool

If validator returns False for key, return False immediately. Otherwise, advance the iterable and store items until an item mapping to key under the key function is seen.

class asyncutils.iterclasses.AChain[T]

Async version of chain() that takes async or sync iterables.

Construct an AChain from the (async) iterables.

__aiter__() types.AsyncGeneratorType[T]

Yield items from the first iterable until exhausted, then start on the second, etc.

classmethod from_iterable(
it_of_its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
) Self

Construct an AChain from it_of_its, an (async) iterable of (async) iterables to chain. If some iterables are chains themselves, their internal iterable of iterables are flattened into that of the returned AChain, which may cause unexpected behaviour when iterating through these sources themselves.

Tip

Since the outer iterable is advanced on demand, a possible use case would be to combine chunks of items from different sources as they arrive.

class asyncutils.iterclasses.APeekable[T]
class asyncutils.iterclasses.APeekable(it: asyncutils._internal.prots.SupportsIteration[T])

Bases: asyncutils._internal.helpers.LoopMixinBase

Async version of more_itertools.peekable.

Wrap an (async) iterable in an asynchronous iterator and sequence APIs, supporting lookahead and prepending.

__aiter__() Self

Return the instance itself.

async __anext__() T

Return the next item, advancing the iterable.

async __getitem__(idx: asyncutils._internal.prots.ValidSlice, /) tuple[T, Ellipsis]
async __getitem__(idx: SupportsIndex, /) T

Slice or index access. Must be awaited.

async can_peek() bool

Check whether any items are left in the underlying iterable without advancing it.

async peek(default: T = ...) T

Return the next item of the underlying iterable without advancing it, or default if the items have run out.

prepend(/, *items: T) None

Yield the prepended items in the order passed in first instead of advancing the underlying iterable.

asyncutils.iters
Functional and composable interface to get async generators from (async) iterables. Many of the algorithms here are taken from more_itertools, but some are unique to async.
However, since they must support both sync and async iterables, they are much less efficient than their sync counterparts.
Classes
Functions

aaccumulate(→ types.AsyncGeneratorType[T])

Async version of itertools.accumulate() that is not a class.

aadjacent(…)

For each item in the (async) iterable it, yield tuples of the form (is_within_dist, item), where is_within_dist is True iff the closest distance to an item satisfying pred is at most dist, and the call to pred is awaited iff await_pred=True is passed.

aall(→ bool)

Async version of all().

aall_equal(→ bool)

Whether all items in the (async) iterable are equal to each other according to the key function. Check for identity rather than equality if strict is True.

aall_unique(…)

Return whether all the items in the (async) iterable it are distinct (according to key, awaited if await_key=True is passed, if passed).

aany(→ bool)

Async version of any().

aappend(→ types.AsyncGeneratorType[T])

Append val to the (async) iterable it.

aargmax(…)

Return the index of the first occurrence of the maximum element in the (async) iterable it according to key, or default if empty.

aargmin(…)

Return the index of the first occurrence of the minimum element in the (async) iterable it according to key, or default if empty.

aargminmax(…)

Return a tuple of the indices of the first occurrences of the minimum and maximum elements in the (async) iterable it according to key, or default if empty.

aawgenf2agenf(→ collections.abc.Callable[P, ...)

Convert a function that returns an awaitable resolving to an async iterable into one returning an async generator.

abefore_and_after(→ tuple[types.AsyncGeneratorType[T], ...)

atakewhile(), but return all remaining items in the second async generator (after the first is consumed).

abfs(→ types.AsyncGeneratorType[T])

Breadth-first search on a start node start, given a function neighbours that returns an (async) iterable of neighbours to be traversed in order. If include_start is True, the start node is yielded first.

abrent(→ tuple[T, int, int])

ac3merge(→ types.AsyncGeneratorType[T])

Async version of functools._c3_merge() that doesn't assume the input is a synchronous iterable over mutable sequences of classes.

acanonical(→ list[T])

Return a canonicalized ordering of the items in it, which may change across different Python invocations or sessions.

acat(…)

Yield the sent value, starting with first (default None).

acollapse(→ types.AsyncGeneratorType[Any])

Flatten the (async) iterable it by at most levels levels, without collapsing objects of types specified in base_typ.

acombinations(→ types.AsyncGeneratorType[tuple[T, ...)

Async version of itertools.combinations() that is not a class.

acombinations_with_replacement(...)

Async version of itertools.combinations_with_replacement() that is not a class.

acompress(→ types.AsyncGeneratorType[T])

Async version of itertools.compress() that is not a class.

aconsume(→ None)

Advance the (async) iterable it by n steps, using a function-scoped executor created on demand where appropriate. If you want the item at the final position, use anth() instead.

aconvolve(→ types.AsyncGeneratorType[T])

Polynomial multiplication with coefficients from the two iterables. The first iterable is advanced on demand, meaning it may be infinite, but the second iterable is exhausted immediately, storing all its items in memory.

acount(…)

Async version of itertools.count() that is not a class.

acount_cycle(→ types.AsyncGeneratorType[tuple[int, T]])

Yield tuples of the form (n, item), where item cycles through the iterable, caching its items during the first cycle, and n is the number of times the iterable has been completely cycled prior to yielding item.

acountdown(→ types.AsyncGeneratorType[int])

Count down from n to zero, excluding zero if it is to appear and include_zero is False (the default), by a step size of step.

acycle(→ types.AsyncGeneratorType[T])

Async version of itertools.cycle() that is not a class.

aderangements(→ types.AsyncGeneratorType[T])

Successive derangements of the elements in it of size r, or all sizes if not passed. Derangements are permutations with no fixed points.

adfs(→ types.AsyncGeneratorType[T])

Depth-first search on a start node start, given a function neighbours that returns an (async) iterable of neighbours to be traversed in order. If include_start is True, the start node is yielded first.

adft(→ types.AsyncGeneratorType[complex])

The discrete Fourier transform. O(n^2), since this library does not specialize in these operations.

adifference(…)

For an iterable with items a, b, c, etc., yield a, func(b, a), func(c, b), dropping a iff yield_initial=False was passed and awaiting the return value iff await_func=True was passed. Essentially the inverse of aaccumulate().

adistinct_permutations(...)

Successive distinct permutations of the elements in it of size r, or all sizes if not passed.

adouble_starmap(→ types.AsyncGeneratorType[T])

Like amap(), but the iterables should yield mappings that are unpacked as arguments to the function.

adropuntil(…)

Drop items from the iterable until the predicate called on the item holds.

adropuntil_exclusive(…)

Like adropuntil() but starts only after dropping the first truthy item.

adropwhile(…)

Async version of itertools.dropwhile() that is not a class.

adropwhile_exclusive(…)

Like adropwhile() but starts only after dropping the first falsy item.

advance_by(→ None)

aevery(→ types.AsyncGeneratorType[T])

Yield every n-th item from an (async) iterable, optionally skipping the first item.

aevery_other(→ types.AsyncGeneratorType[T])

Yield every other item from an (async) iterable, optionally skipping the first item.

afactor(→ types.AsyncGeneratorType[int])

Generate the prime factors of n asynchronously. Do not rely on the resultant order.

afilter(…)

Async version of filter that is not a class.

afilterfalse(…)

Async version of itertools.filterfalse() that is not a class.

afirst(→ T)

Return the first item in the (async) iterable it, or default if passed and it is empty.

afirstfalse(→ T)

Return the first item in the (async) iterable it that fails the predicate, or default if passed and there is no such item, and raise StopAsyncIteration otherwise.

afirstfalse_or_first(…)

afirstfalse_or_last(…)

afirsttrue(→ T)

Return the first item in the (async) iterable it that satisfies the predicate, or default if passed and there is no such item, and raise StopAsyncIteration otherwise.

afirsttrue_or_first(…)

afirsttrue_or_last(…)

aflatten(→ types.AsyncGeneratorType[T])

Flatten one level of nesting using AChain and return an async iterator over it.

aflatten_tensor(→ types.AsyncGeneratorType[Any])

acollapse(), but using a different, more memory-efficient strategy that does not support the levels parameter.

aforever(→ types.AsyncGeneratorType[None])

Yield None forever. Equivalent to arepeat(None).

afreivalds(→ bool)

Determine if the matrix product of A and B equals C. This is the probabilistic Freivalds algorithm. O(kn^2) time, with a false positive rate of at most 2^(-k) and no false negatives.

agather(→ list[T])

Wrap asyncio.gather() to accept (async) iterables as the first argument, so that unpacking is not needed.

agives(→ types.AsyncGeneratorType[T])

Yield the given value, then return.

agroupby(…)

Async version of itertools.groupby() that is not a class.

agroupby_transform(…)

Async version of more_itertools.groupby_transform().

agrouper(→ types.AsyncGeneratorType[tuple[T | None, ...)

aguessmax(…)

Optimal solution to the secretary problem, using key to guess the maximum item, which is the candidate chosen, with 36.8% accuracy, by finding the maximum among the first 36.8% of the (async) iterable and then returning the first item greater than that afterwards, in O(1) space. reject_cb is called on every rejected candidate once rejected, its return value awaited if await_cb=True is passed, and no more than one candidate is ever stored. This Numberphile video proves that the approach used is best.

aguessmin(…)

Like aguessmax(), but guesses the minimum item instead.

aichunked(...)

aidft(→ types.AsyncGeneratorType[complex])

The inverse discrete Fourier transform. O(n^2) just like adft().

aiequals(→ bool)

ailen(→ int)

Return the length of the (async) iterable it, consuming it entirely.

ainterleave_evenly(→ types.AsyncGeneratorType[T])

Interleave items of the iterables evenly according to the lengths if passed, and determined by calling the __len__() method on the iterables if present otherwise.

ainterleave_randomly(→ types.AsyncGeneratorType[T])

Interleave items of the iterables randomly, skipping exhausted iterables.

ainterleave_stopearly(→ types.AsyncGeneratorType[T])

Yield the items from the iterables in a round-robin fashion until at least one is exhausted.

aintersend(→ types.AsyncGeneratorType[tuple[T, R]])

Feed i1 and i2 into each other and yield tuples of the form (yielded_from_i1, yielded_from_i2).

aintersperse(→ types.AsyncGeneratorType[T])

Yield e, then the next n items in it, and repeat until it is exhausted.

aisempty(→ bool)

Return whether the (async) iterable it is empty.

aislice(…)

Async version of itertools.islice() that is not a class.

aisprime(→ bool)

Probabilistically test for primality of n. O(log^3 n), with false-positive rate below 2^(-128) for integers above 10^24.

aiter_idx(→ types.AsyncGeneratorType[int])

Yield the indices at which value occurs in it within start and stop.

aiterate(→ types.AsyncGeneratorType[T])

Yield start, then the awaited output of f called on the previous output repeatedly.

aiterexcept(→ types.AsyncGeneratorType[T])

Yield the awaited output of first, then f called with no arguments repeatedly until an exception present in exc occurs.

alast(→ T)

Return the last item in the (async) iterable it, or default if passed and it is empty.

all_max(…)

all_min(…)

aloops(→ types.AsyncGeneratorType[None])

Yield None n times. Equivalent to base.take(aforever(), n) and arepeat(None, n), but without creating intermediate integers.

amap(…)

Async version of map that is not a class, with await_ dictating whether the return value of the function is to be awaited before yielding.

amapif(…)

Essentially the restriction of amultimapif() to one (async) iterable.

amatmul(→ types.AsyncGeneratorType[tuple[T, Ellipsis]])

Matrix multiplication of M and N. O(n^3) time, since this library does not specialize in these operations.

amatprod(→ T)

Return the product of the matrices in the (async) iterable, preceded by start if passed.

amax(…)

Async version of max().

amerge_sorted_by(…)

Async version of heapq.merge().

amin(…)

Async version of min().

aminmax(…)

Return a tuple of the smallest item and the largest item in the iterable or among the positional arguments by making a single pass. If the iterable is empty, return default. O(1) space and O(n) time.

aminmax_keyed(…)

Like aminmax(), but performs comparisons according to the return value of key.

amultifilter(…)

Composition of afilter() and azip().

amultifilterfalse(…)

Composition of afilterfalse() and azip().

amultimapif(…)

Composition of astarmap(), afilter() and azip().

amultistarfilter(…)

Composition of astarfilter() and azip().

amultistarfilterfalse(…)

Composition of astarfilterfalse() and azip().

amultistarmapif(…)

Composition of astarmap() and amultistarfilter().

ancycles(→ types.AsyncGeneratorType[T])

Yield the items in the (async) iterable it over and over for a total of n cycles.

anth(→ T)

Return the n-th item of the (async) iterable it, or default if passed and there is no such item.

anth_combination(→ types.AsyncGeneratorType[T])

Return the n-th combination of r elements from the input iterable it, in lexicographic order.

anth_combination_with_replacement(→ tuple[T, Ellipsis])

Return the n-th combination of r elements from the input iterable it, in lexicographic order, allowing individual elements to be repeated.

anth_or_last(→ T)

Return the n-th item in the (async) iterable it, or the last item if out of bounds, or default if passed and it is empty.

anth_permutation(→ tuple[T, Ellipsis])

Return the n-th permutation of r elements from the input iterable it, in lexicographic order.

anth_product(→ tuple[T, Ellipsis])

Return the n-th item of the Cartesian product of the input iterables its, in lexicographic order, with each iterable repeated repeat times.

aonline_sorter(…)

aouter_product(→ types.AsyncGeneratorType[list[V]])

apadded(→ types.AsyncGeneratorType[T])

Yield the items in the (async) iterable it, followed by fillvalue repeatedly, such that the iterable is fully consumed and the result has length at least n if passed.

apadnone(→ types.AsyncGeneratorType[T | None])

Yield the items in the (async) iterable it, followed by None repeatedly, such that the iterable is fully consumed and the result has length at least n if passed.

apairwise(→ types.AsyncGeneratorType[tuple[T, T]])

Async version of itertools.pairwise() that is not a class.

apartition(→ tuple[types.AsyncGeneratorType[T], ...)

Return a tuple (fg, tg). tg is an async generator yielding the items in it passing the predicate, and fg the others.

apermutations(→ types.AsyncGeneratorType[tuple[T, ...)

Async version of itertools.permutations() that is not a class.

apolynomial_derivative(→ types.AsyncGeneratorType[T])

Compute the coefficients of the derivative of a polynomial. Both input and output iterables are in order of descending powers.

apolynomial_eval(→ T)

Evaluate a polynomial at x given its coefficients in order of descending powers.

apolynomial_from_roots(→ types.AsyncGeneratorType[T])

Generate the coefficients of a polynomial given its roots in order of descending powers.

apowers(→ types.AsyncGeneratorType[T])

Yield start, start*base, start*base*base, ...

apowers_of_two(→ types.AsyncGeneratorType[int])

Optimized version of apowers() using bit shift operations for powers of two, four, eight, etc. Yield init<<init_shift, init<<init_shift+shift, init<<init_shift+2*shift, ...

apowerset(→ types.AsyncGeneratorType[tuple[T, Ellipsis]])

Yield all the subsets of the (async) iterable it (by index!) as tuples, starting with the empty tuple.

apowerset_of_sets(…)

Yield all the subsets of the items in the (async) iterable of hashable objects after consuming it at once and removing duplicates, as frozenset's if frozen is True (the default) and set's otherwise.

aprepend(→ types.AsyncGeneratorType[T])

Prepend val to the (async) iterable it.

aprod(→ T)

Return the product of the items in the (async) iterable, preceded by start if passed.

aproduct(…)

Async version of itertools.product() that is not a class.

aquantify(→ int)

Return the number of items in the (async) iterable for which the predicate is true.

arandom_combination(→ types.AsyncGeneratorType[T])

Draw r items at random from the input iterable it, without replacement.

arandom_combination_with_replacement(...)

Draw r items at random from the input iterable it, with replacement.

arandom_derangement(→ tuple[T, Ellipsis])

Generate a random derangement of items in the (async) iterable it.

arandom_permutation(→ types.AsyncGeneratorType[T])

Choose a random permutation of the elements in it of size r, or all sizes if not passed.

arandom_product(→ types.AsyncGeneratorType[T])

Draw n items from each of the input iterables its at random.

arange(…)

Async version of range that is not a class.

arepeat(→ types.AsyncGeneratorType[T])

Async version of itertools.repeat() that is not a class.

arepeat_each(→ types.AsyncGeneratorType[T])

Yield each item in the (async) iterable it exactly n times before advancing.

arepeat_func(→ types.AsyncGeneratorType[T])

Call the async function f with arguments a repeatedly for times times, or indefinitely if times is not passed, and yield the results awaited.

arepeat_last(→ types.AsyncGeneratorType[T])

Yield all the items in the (async) iterable it, then keep yielding the last item forever, or default if the iterable was empty, stopping if it was not passed. If default was RAISE, raise ItemsExhausted.

areshape(…)

Change the shape of a tensor according to shape. For an integer shape, the matrix must be 2D and shape is the number of output columns.

areversed(→ types.AsyncGeneratorType[T])

Reverse an (async) iterable, calling its __reversed__() method and converting the result into an async generator if present, and fall back to consuming and saving all the items and yielding them in reverse order.

aroundrobin(→ types.AsyncGeneratorType[T])

Yield items from the given (async) iterables in round-robin order, skipping exhausted iterables. Prefer over aroundrobin2() for less iterables.

aroundrobin2(→ types.AsyncGeneratorType[T])

Yield items from the given (async) iterables in round-robin order, skipping exhausted iterables. Prefer over aroundrobin() for more iterables.

arunlength_decode(→ types.AsyncGeneratorType[T])

Inverse of the above, but takes any (async) iterable and always gives an async generator.

arunlength_encode(→ types.AsyncGeneratorType[tuple[T, ...)

Compress an (async) iterable into an async generator of pairs with run-length encoding. Items in the result are in the form (item, count), where item is an item from the input iterable and count is the number of times it is repeated consecutively.

arunning_mean(→ types.AsyncGeneratorType[T])

Repeatedly yield the mean of the items in the iterable so far, and advance the iterable.

arunning_median(→ types.AsyncGeneratorType[T])

Yield the median of all the items seen from it within a window of size maxlen, then advance it.

asample_l(→ list[T])

Chooses k items from an (async) iterable of items, where each item is chosen with equal probability. rrange and rand should be the randrange() and random() methods of a random device respectively. This is Algorithm L.

asample_weighted(→ list[T])

Choose k items from an (async) iterable of (item, weight) pairs, where the probability of each item being chosen is proportional to its weight. rrange and rand should be the randrange() and random() methods of a random device respectively. This is the A-Chao with Jumps reservoir sampling algorithm.

asattolo(→ list[T])

Return a list representing a random full-length permutation of the items in it.

asendstream(→ types.AsyncGeneratorType[T])

Feed i2 into i1 and yield the results.

aserialize(→ types.AsyncGeneratorType[T])

Protect an (async) iterable from being consumed by many parties concurrently by applying an async lock.

aside_effect(…)

asieve(→ types.AsyncGeneratorType[int])

Yield prime numbers strictly smaller than n in order in an async generator.

asliced(→ types.AsyncGeneratorType[T])

asorted(…)

Async version of sorted(). O(n log n) time and O(n) space, but nowhere near as optimized as the builtin version.

asplitat(→ types.AsyncGeneratorType[list[T]])

Split an async iterator at each item satisfying pred, with keep_sep dictating whether the separator is to be included as the last item of each list.

aspy(→ tuple[types.AsyncGeneratorType[T], ...)

Return an async generator containing the first n items, and another containing all the original items.

astarfilter(…)

Filter an (async) iterable of tuples of items, yielding only those tuples for which the predicate returns a truthy value when called on the tuple unpacked.

astarfilterfalse(…)

Filter an (async) iterable of tuples of items, yielding only those tuples for which the predicate returns a falsy value when called on the tuple unpacked.

astarmap(…)

Async version of itertools.starmap() that is not a class. await_ specifies whether to await the return value of the transformation function.

astarmap_with_kwds(→ types.AsyncGeneratorType[T])

Like amap(), but the iterable should yield tuples of the form (args, kwargs), where args is an iterable of positional arguments and kwargs is a mapping of keyword arguments.

asubslices(→ types.AsyncGeneratorType[tuple[T, Ellipsis]])

asubstrings(), but yield all subslices containing the first item first in ascending order of length, then all subslices containing the second item but not the first, and so on.

asubstr_indices(…)

Yield tuples of the form (substr, start, end), where substr is a contiguous subsequence of seq starting at index start and ending at index end-1 (such that its length is end-start).

asubstrings(→ types.AsyncGeneratorType[tuple[T, Ellipsis]])

Yield all contiguous subsequences of the (async) iterable it as tuples, in increasing order of length.

asum(→ T)

Return the sum of the items in the (async) iterable, preceded by start if passed.

asum_of_squares(→ T)

Return the sum of squares of items in an (async) iterable of numbers as a number of the same type.

asumprod(→ T)

Return the sum of products of items in two iterables of numbers as a number of the same type. Not as precise as math.sumprod() for floating-point numbers, but supports async iterables.

at_most_one(…)

atabulate(…)

Composition of amap() and acount().

atabulate_finite(…)

atail(→ types.AsyncGeneratorType[T])

Yield the last n items from the (async) iterable it.

atakeuntil(…)

Take items from the iterable until the predicate called on the item holds.

atakeuntil_inclusive(…)

Like atakewhile() but stops only after yielding the first truthy item.

atakewhile(…)

Async version of itertools.takewhile() that is not a class.

atakewhile_inclusive(…)

Like atakewhile() but stops only after yielding the first falsy item.

atranspose(→ types.AsyncGeneratorType[tuple[T, Ellipsis]])

Compute the transpose of a matrix.

atriplewise(→ types.AsyncGeneratorType[tuple[T, T, T]])

Yield overlapping triples of items from an (async) iterable.

aunique(→ types.AsyncGeneratorType[T])

Yield unique elements from it in sorted order, according to key, which should not be too expensive. If reverse is True, yield in descending order.

aunique_everseen(…)

Yield items from the (async) iterable it, without yielding items already previously yielded.

aunique_justseen(…)

Yield items from the (async) iterable it, without yielding consecutive duplicate items.

aunique_to_each(→ types.AsyncGeneratorType[T])

Given multiple (async) iterables, yield every item that is only seen in exactly one of the iterables.

aunzip(…)

awindowed_complete(...)

Yield tuples of the form (prev, window, next), where window is a tuple of n items from the (async) iterable it, and prev and next are tuples of all the items before and after that window, respectively. Consumes and caches the whole iterable, so use with caution.

awrap(→ types.AsyncGeneratorType[T])

Wrap the (async) iterable it by yielding start first, then the items in it, then end.

awrapf(…)

Call before when the iterable starts, then yield the items in it, then call after as long as before did not raise and the iterable was converted to an async generator successfully. The return value of each function is awaited if it doesn't raise TypeError.

azip(…)

Async version of zip that is not a class.

azip_offset(…)

aziplongest(…)

Async version of itertools.zip_longest() that is not a class. The first overload does not accept fillvalue, because passing it with only one iterable does not make sense.

basic_collect(→ list[T])

Return a list of the first n items in the (async) iterable it, signalling no error if there are not enough items.

batch(→ types.AsyncGeneratorType[list[T]])

More flexible but slightly slower implementation of batch2(), supporting timeouts waiting for each item, that raises ValueError instead of ItemsExhausted in the case of the length of the iterable being indivisible by the batch size.

batch2(…)

Batch an (async) iterable into an async generator of lists. If strict=True is specified, raise ItemsExhausted on the last batch if it is discovered then that the iterable does not have enough items for a complete batch.

batch_process(→ types.AsyncGeneratorType[R])

Apply processor to each batch of size size in items and yield the results awaited.

buffer(→ types.AsyncGeneratorType[T])

circular_shifts(→ types.AsyncGeneratorType[tuple[T, ...)

cloned(→ types.AsyncGeneratorType[T])

Yield copies of the items in the (async) iterable it, as returned by copy().

coalesce(…)

counts(…)

decreasing_runs(→ types.AsyncGeneratorType[list[T]])

diff_with(→ FirstMisMatch[T, ...)

distribute(…)

duplicates(…)

empty_agen(→ types.AsyncGeneratorType[Never])

Return an async generator that yields nothing. Due to async generator finalization issues, this is not a constant like yield_to_event_loop.

extract(→ list[asyncio.Future[T]])

extract_monotonic(→ types.AsyncGeneratorType[T])

filter_identical(→ types.AsyncGeneratorType[T])

flat_map(…)

Async version of map that is not a class, with await_ dictating whether the return value of the function is to be awaited before yielding.

fmap(→ list[T])

Return a list of the results of calling each async function in the first argument (an (async) iterable of functions), with the provided arguments.

fmap_parallel(→ types.AsyncGeneratorType[T])

Like fmap_sequential(), but starts background tasks for each call.

fmap_sequential(→ types.AsyncGeneratorType[T])

Like fmap(), but only call a function after the last completes and the result is gotten.

fuse(…)

gray_product(…)

group_from(→ types.AsyncGeneratorType[tuple[T, ...)

Yield tuples of the form (key, group), where group is an async generator taken from values and corresponding to the same run of keys in keys. If strict=False is passed, an error is not raised when keys and values differ in length.

hamming_dist(→ int)

Return the Hamming distance between two (async) iterables, using cmpeq to check for equality if passed.

increasing_runs(→ types.AsyncGeneratorType[list[T]])

is_sorted(…)

iter_task(→ asyncio.Task[float])

Return a task that calls summaryf on the passed (async) iterable and returns the time taken to run it. By default, summaryf consumes it fully.

iterate_with_key(…)

locate(…)

longest_common_prefix(→ types.AsyncGeneratorType[T])

lstrip(…)

map_if_else(…)

map_on_map(…)

Apply a transformation on an (async) iterable on top of another.

map_windows(…)

mark_ends(→ types.AsyncGeneratorType[tuple[bool, bool, T]])

mat_vec_mul(→ types.AsyncGeneratorType[int])

Multiplication of a matrix M and a vector V. O(n^2).

merge(→ types.AsyncGeneratorType[T])

pad_using(…)

partial_product(…)

partitions(→ types.AsyncGeneratorType[list[tuple[T, ...)

product_index(…)

rstrip(…)

scan(…)

sort_together(…)

split_when(→ types.AsyncGeneratorType[list[T]])

stagger(…)

strip(…)

tee(…)

to_deque(→ collections.deque[T])

Collect all items in the (async) iterable it into a deque.

to_list(→ list[T])

Collect all items of an async iterable into a list. Faster than collect().

to_set(…)

Collect all items in the (async) iterable it into a set or frozenset depending on the frozen parameter (False by default).

to_tuple(→ tuple[T, Ellipsis])

Convert the output of to_list() into a tuple.

vecs_eq(→ bool)

Whether the vectors u and v are equal according to cmpeq called on each pair of items from iterating through them in parallel. If strict is False (default True), may return True even for differently-sized vectors.

window(→ types.AsyncGeneratorType[tuple[T, Ellipsis], ...)

Window an async iterable into an async generator of tuples of the specified size and step. You can send in a tuple (size, step) to change the behaviour of the iterator.

Module Contents
class asyncutils.iters.FirstMisMatch[T, R]

Bases: NamedTuple

async collect_left() list[T]
async collect_right() list[R]
remainder(strict: bool = ...) types.AsyncGeneratorType[tuple[T, R]]
i: int
lrem: types.AsyncGeneratorType[T]
rrem: types.AsyncGeneratorType[R]
class asyncutils.iters.Longer[T]

Bases: NamedTuple

async collect() list[T]
i: int
rrem: types.AsyncGeneratorType[T]
class asyncutils.iters.Shorter[T]

Bases: NamedTuple

async collect() list[T]
i: int
lrem: types.AsyncGeneratorType[T]
asyncutils.iters.aaccumulate[T](
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T, T], T] = ...,
*,
initial: T | None = ...,
) types.AsyncGeneratorType[T]

Async version of itertools.accumulate() that is not a class.

asyncutils.iters.aadjacent[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
dist: int = ...,
*,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[bool, T]]
asyncutils.iters.aadjacent(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
dist: int = ...,
*,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[bool, T]]

For each item in the (async) iterable it, yield tuples of the form (is_within_dist, item), where is_within_dist is True iff the closest distance to an item satisfying pred is at most dist, and the call to pred is awaited iff await_pred=True is passed.

async asyncutils.iters.aall(it: asyncutils._internal.prots.SupportsIteration[object]) bool

Async version of all().

async asyncutils.iters.aall_equal[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], object] = ...,
strict: bool = ...,
) bool

Whether all items in the (async) iterable are equal to each other according to the key function. Check for identity rather than equality if strict is True.

async asyncutils.iters.aall_unique[T](it: asyncutils._internal.prots.SupportsIteration[T], key: None = ...) bool
async asyncutils.iters.aall_unique(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
*,
await_key: Literal[False] = ...,
) bool
async asyncutils.iters.aall_unique(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
*,
await_key: Literal[True],
) bool

Return whether all the items in the (async) iterable it are distinct (according to key, awaited if await_key=True is passed, if passed).

async asyncutils.iters.aany(it: asyncutils._internal.prots.SupportsIteration[object]) bool

Async version of any().

asyncutils.iters.aappend[T](val: T, it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Append val to the (async) iterable it.

async asyncutils.iters.aargmax[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
default: int = ...,
*,
await_key: Literal[False] = ...,
) int
async asyncutils.iters.aargmax(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
default: int = ...,
*,
await_key: Literal[True],
) int
async asyncutils.iters.aargmax(it: asyncutils._internal.prots.SupportsIteration[T], *, default: int = ...) int

Return the index of the first occurrence of the maximum element in the (async) iterable it according to key, or default if empty.

async asyncutils.iters.aargmin[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
default: int = ...,
*,
await_key: Literal[False] = ...,
) int
async asyncutils.iters.aargmin(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
default: int = ...,
*,
await_key: Literal[True],
) int
async asyncutils.iters.aargmin(it: asyncutils._internal.prots.SupportsIteration[T], *, default: int = ...) int

Return the index of the first occurrence of the minimum element in the (async) iterable it according to key, or default if empty.

async asyncutils.iters.aargminmax[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
*,
await_key: Literal[False] = ...,
) tuple[int, int]
async asyncutils.iters.aargminmax(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
*,
await_key: Literal[True],
) tuple[int, int]
async asyncutils.iters.aargminmax(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
default: R,
*,
await_key: Literal[False] = ...,
) tuple[int, int] | R
async asyncutils.iters.aargminmax(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
default: R,
*,
await_key: Literal[True],
) tuple[int, int] | R
async asyncutils.iters.aargminmax(it: asyncutils._internal.prots.SupportsIteration[T]) tuple[int, int]
async asyncutils.iters.aargminmax(it: asyncutils._internal.prots.SupportsIteration[T], *, default: R) tuple[int, int] | R

Return a tuple of the indices of the first occurrences of the minimum and maximum elements in the (async) iterable it according to key, or default if empty.

asyncutils.iters.aawgenf2agenf[T, **P](
f: collections.abc.Callable[P, collections.abc.AsyncIterable[T]],
/,
) collections.abc.Callable[P, types.AsyncGeneratorType[T]]

Convert a function that returns an awaitable resolving to an async iterable into one returning an async generator.

asyncutils.iters.abefore_and_after[T](
pred: collections.abc.Callable[[T], object],
it: asyncutils._internal.prots.SupportsIteration[T],
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]

atakewhile(), but return all remaining items in the second async generator (after the first is consumed).

asyncutils.iters.abfs[T: collections.abc.Hashable](
start: T,
neighbours: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsIteration[T]],
*,
include_start: bool = ...,
) types.AsyncGeneratorType[T]

Breadth-first search on a start node start, given a function neighbours that returns an (async) iterable of neighbours to be traversed in order. If include_start is True, the start node is yielded first.

async asyncutils.iters.abrent[T](next_node: collections.abc.Callable[[T], collections.abc.Awaitable[T]], start: T, /) tuple[T, int, int]
Brent’s algorithm for cycle detection, assuming that a cycle is indeed present, given a function next_node returning the next node from the previous.
Return a tuple (node, la, mu), where node is the first node involved in a cycle, mu its index (the least number of times next_node was applied to get node), and la the cycle length.

Note

next_node should be deterministic. Also, if there is no cycle, the algorithm hangs indefinitely.

asyncutils.iters.ac3merge[T](
seqs: asyncutils._internal.prots.SupportsIteration[collections.abc.MutableSequence[T]],
) types.AsyncGeneratorType[T]

Async version of functools._c3_merge() that doesn’t assume the input is a synchronous iterable over mutable sequences of classes.

asyncutils.iters.acanonical[T](it: asyncutils._internal.prots.SupportsIteration[T]) list[T]

Return a canonicalized ordering of the items in it, which may change across different Python invocations or sessions.

asyncutils.iters.acat[T](first: T) types.AsyncGeneratorType[T, T]
asyncutils.iters.acat(first: None = ...) types.AsyncGeneratorType[T | None, T | None]

Yield the sent value, starting with first (default None).

asyncutils.iters.acollapse(
it: asyncutils._internal.prots.SupportsIteration[object],
base_typ: tuple[type, Ellipsis] | type = ...,
levels: int | None = ...,
) types.AsyncGeneratorType[Any]

Flatten the (async) iterable it by at most levels levels, without collapsing objects of types specified in base_typ.

asyncutils.iters.acombinations[T](
it: asyncutils._internal.prots.SupportsIteration[T],
r: int,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Async version of itertools.combinations() that is not a class.

asyncutils.iters.acombinations_with_replacement[T](
it: asyncutils._internal.prots.SupportsIteration[T],
r: int,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Async version of itertools.combinations_with_replacement() that is not a class.

asyncutils.iters.acompress[T](
data: asyncutils._internal.prots.SupportsIteration[T],
selectors: asyncutils._internal.prots.SupportsIteration[object],
) types.AsyncGeneratorType[T]

Async version of itertools.compress() that is not a class.

async asyncutils.iters.aconsume[T](it: asyncutils._internal.prots.SupportsIteration[T], n: int | None = ...) None

Advance the (async) iterable it by n steps, using a function-scoped executor created on demand where appropriate. If you want the item at the final position, use anth() instead.

asyncutils.iters.aconvolve[T: (int, float, complex)](
signal: asyncutils._internal.prots.SupportsIteration[T],
kernel: asyncutils._internal.prots.SupportsIteration[T],
) types.AsyncGeneratorType[T]

Polynomial multiplication with coefficients from the two iterables. The first iterable is advanced on demand, meaning it may be infinite, but the second iterable is exhausted immediately, storing all its items in memory.

asyncutils.iters.acount(start: int = ..., step: int = ...) types.AsyncGeneratorType[int]
asyncutils.iters.acount(start: float, step: int = ...) types.AsyncGeneratorType[float]
asyncutils.iters.acount(start: float, step: float) types.AsyncGeneratorType[float]
asyncutils.iters.acount(*, step: float) types.AsyncGeneratorType[float]

Async version of itertools.count() that is not a class.

asyncutils.iters.acount_cycle[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int | None = ...,
) types.AsyncGeneratorType[tuple[int, T]]

Yield tuples of the form (n, item), where item cycles through the iterable, caching its items during the first cycle, and n is the number of times the iterable has been completely cycled prior to yielding item.

asyncutils.iters.acountdown(n: int, step: int = ..., *, include_zero: bool = ...) types.AsyncGeneratorType[int]

Count down from n to zero, excluding zero if it is to appear and include_zero is False (the default), by a step size of step.

asyncutils.iters.acycle[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Async version of itertools.cycle() that is not a class.

asyncutils.iters.aderangements[T](it: asyncutils._internal.prots.SupportsIteration[T], r: int | None = ...) types.AsyncGeneratorType[T]

Successive derangements of the elements in it of size r, or all sizes if not passed. Derangements are permutations with no fixed points.

asyncutils.iters.adfs[T: collections.abc.Hashable](
start: T,
neighbours: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsIteration[T]],
*,
include_start: bool = ...,
) types.AsyncGeneratorType[T]

Depth-first search on a start node start, given a function neighbours that returns an (async) iterable of neighbours to be traversed in order. If include_start is True, the start node is yielded first.

asyncutils.iters.adft(xarr: asyncutils._internal.prots.SupportsIteration[complex], /) types.AsyncGeneratorType[complex]

The discrete Fourier transform. O(n^2), since this library does not specialize in these operations.

asyncutils.iters.adifference[T, R](
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T, T], R],
*,
yield_initial: Literal[False],
await_func: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.adifference(
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T, T], collections.abc.Awaitable[R]],
*,
yield_initial: Literal[False],
await_func: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.adifference(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
yield_initial: bool = ...,
await_func: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.adifference(
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T, T], collections.abc.Awaitable[T]],
*,
yield_initial: Literal[True] = ...,
await_func: Literal[True],
) types.AsyncGeneratorType[T]

For an iterable with items a, b, c, etc., yield a, func(b, a), func(c, b), dropping a iff yield_initial=False was passed and awaiting the return value iff await_func=True was passed. Essentially the inverse of aaccumulate().

asyncutils.iters.adistinct_permutations[T](
it: asyncutils._internal.prots.SupportsIteration[T],
r: int | None = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Successive distinct permutations of the elements in it of size r, or all sizes if not passed.

asyncutils.iters.adouble_starmap[T](
f: collections.abc.Callable[Ellipsis, T],
it: asyncutils._internal.prots.SupportsIteration[collections.abc.Mapping[str, Any]],
/,
) types.AsyncGeneratorType[T]

Like amap(), but the iterables should yield mappings that are unpacked as arguments to the function.

asyncutils.iters.adropuntil[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.adropuntil(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]

Drop items from the iterable until the predicate called on the item holds.

asyncutils.iters.adropuntil_exclusive[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.adropuntil_exclusive(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]

Like adropuntil() but starts only after dropping the first truthy item.

asyncutils.iters.adropwhile[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.adropwhile(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]

Async version of itertools.dropwhile() that is not a class.

asyncutils.iters.adropwhile_exclusive[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.adropwhile_exclusive(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]

Like adropwhile() but starts only after dropping the first falsy item.

async asyncutils.iters.advance_by(it: asyncutils._internal.prots.SupportsIteration[object], n: int) None
asyncutils.iters.aevery[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int,
*,
skip_first: bool = ...,
) types.AsyncGeneratorType[T]

Yield every n-th item from an (async) iterable, optionally skipping the first item.

asyncutils.iters.aevery_other[T](
it: asyncutils._internal.prots.SupportsIteration[T],
*,
skip_first: bool = ...,
) types.AsyncGeneratorType[T]

Yield every other item from an (async) iterable, optionally skipping the first item.

asyncutils.iters.afactor(n: int) types.AsyncGeneratorType[int]

Generate the prime factors of n asynchronously. Do not rely on the resultant order.

asyncutils.iters.afilter[T](
f: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afilter(
f: collections.abc.Callable[[T], collections.abc.Awaitable[object]] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[True],
) types.AsyncGeneratorType[T]

Async version of filter that is not a class.

asyncutils.iters.afilterfalse[T](
f: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afilterfalse(
f: collections.abc.Callable[[T], collections.abc.Awaitable[object]] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[True],
) types.AsyncGeneratorType[T]

Async version of itertools.filterfalse() that is not a class.

async asyncutils.iters.afirst[T](it: asyncutils._internal.prots.SupportsIteration[T], default: T = ...) T

Return the first item in the (async) iterable it, or default if passed and it is empty.

async asyncutils.iters.afirstfalse[T](
it: asyncutils._internal.prots.SupportsIteration[T],
default: T | None = ...,
pred: collections.abc.Callable[[T], object] = ...,
) T

Return the first item in the (async) iterable it that fails the predicate, or default if passed and there is no such item, and raise StopAsyncIteration otherwise.

asyncutils.iters.afirstfalse_or_first[T](
it: asyncutils._internal.prots.SupportsIteration[T],
*,
pred: collections.abc.Callable[[T], object] | None = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afirstfalse_or_first(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T,
pred: collections.abc.Callable[[T], object] | None = ...,
*,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afirstfalse_or_first(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.afirstfalse_or_first(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T,
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
*,
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.afirstfalse_or_last[T](
it: asyncutils._internal.prots.SupportsIteration[T],
*,
pred: collections.abc.Callable[[T], object] | None = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afirstfalse_or_last(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T,
pred: collections.abc.Callable[[T], object] | None = ...,
*,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afirstfalse_or_last(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.afirstfalse_or_last(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T,
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
*,
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
async asyncutils.iters.afirsttrue[T](
it: asyncutils._internal.prots.SupportsIteration[T],
default: T | None = ...,
pred: collections.abc.Callable[[T], object] = ...,
) T

Return the first item in the (async) iterable it that satisfies the predicate, or default if passed and there is no such item, and raise StopAsyncIteration otherwise.

asyncutils.iters.afirsttrue_or_first[T](
it: asyncutils._internal.prots.SupportsIteration[T],
*,
pred: collections.abc.Callable[[T], object] | None = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afirsttrue_or_first(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T,
pred: collections.abc.Callable[[T], object] | None = ...,
*,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afirsttrue_or_first(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.afirsttrue_or_first(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T,
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
*,
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.afirsttrue_or_last[T](
it: asyncutils._internal.prots.SupportsIteration[T],
*,
pred: collections.abc.Callable[[T], object] | None = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afirsttrue_or_last(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T,
pred: collections.abc.Callable[[T], object] | None = ...,
*,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.afirsttrue_or_last(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.afirsttrue_or_last(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T,
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
*,
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.aflatten[T](
it: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
) types.AsyncGeneratorType[T]

Flatten one level of nesting using AChain and return an async iterator over it.

asyncutils.iters.aflatten_tensor(
tensor: asyncutils._internal.prots.SupportsIteration[object],
base_typ: tuple[type, Ellipsis] | type = ...,
) types.AsyncGeneratorType[Any]

acollapse(), but using a different, more memory-efficient strategy that does not support the levels parameter.

asyncutils.iters.aforever() types.AsyncGeneratorType[None]

Yield None forever. Equivalent to arepeat(None).

async asyncutils.iters.afreivalds(
A: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[int]],
B: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[int]],
C: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[int]],
k: int = ...,
) bool

Determine if the matrix product of A and B equals C. This is the probabilistic Freivalds algorithm. O(kn^2) time, with a false positive rate of at most 2^(-k) and no false negatives.

async asyncutils.iters.agather[T](
it_of_its: asyncutils._internal.prots.SupportsIteration[collections.abc.Awaitable[T]],
return_exceptions: bool = ...,
) list[T]

Wrap asyncio.gather() to accept (async) iterables as the first argument, so that unpacking is not needed.

asyncutils.iters.agives[T](x: T, /) types.AsyncGeneratorType[T]

Yield the given value, then return.

asyncutils.iters.agroupby[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], T] = ...,
) types.AsyncGeneratorType[tuple[T, types.AsyncGeneratorType[T]]]
asyncutils.iters.agroupby(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], R],
) types.AsyncGeneratorType[tuple[R, types.AsyncGeneratorType[T]]]

Async version of itertools.groupby() that is not a class.

asyncutils.iters.agroupby_transform[T](
it: asyncutils._internal.prots.SupportsIteration[T],
*,
vf: None = ...,
rf: None = ...,
await_kf: Literal[False] = ...,
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, types.AsyncGeneratorType[T]]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], R],
vf: None = ...,
rf: None = ...,
*,
await_kf: Literal[False] = ...,
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, types.AsyncGeneratorType[T]]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
vf: None = ...,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], S],
await_kf: Literal[False] = ...,
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
vf: None = ...,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], collections.abc.Awaitable[S]],
await_kf: Literal[False] = ...,
await_vf: Literal[False] = ...,
await_rf: Literal[True],
) types.AsyncGeneratorType[tuple[T, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], R],
*,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], S],
await_kf: Literal[False] = ...,
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], R],
vf: None,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], S],
*,
await_kf: Literal[False] = ...,
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], R],
*,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], collections.abc.Awaitable[S]],
await_kf: Literal[False] = ...,
await_vf: Literal[False] = ...,
await_rf: Literal[True],
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], R],
vf: None,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], collections.abc.Awaitable[S]],
*,
await_kf: Literal[False] = ...,
await_vf: Literal[False] = ...,
await_rf: Literal[True],
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
vf: None = ...,
rf: None = ...,
*,
await_kf: Literal[True],
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, types.AsyncGeneratorType[T]]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
*,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], S],
await_kf: Literal[True],
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
vf: None,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], S],
*,
await_kf: Literal[True],
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
*,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], collections.abc.Awaitable[S]],
await_kf: Literal[True],
await_vf: Literal[False] = ...,
await_rf: Literal[True],
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
vf: None,
rf: collections.abc.Callable[[types.AsyncGeneratorType[T]], collections.abc.Awaitable[S]],
*,
await_kf: Literal[True],
await_vf: Literal[False] = ...,
await_rf: Literal[True],
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
vf: collections.abc.Callable[[T], V],
rf: None = ...,
*,
await_kf: Literal[True],
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, types.AsyncGeneratorType[V]]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
vf: collections.abc.Callable[[T], V],
rf: collections.abc.Callable[[types.AsyncGeneratorType[V]], S],
*,
await_kf: Literal[True],
await_vf: Literal[False] = ...,
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
vf: collections.abc.Callable[[T], V],
rf: collections.abc.Callable[[types.AsyncGeneratorType[V]], collections.abc.Awaitable[S]],
*,
await_kf: Literal[True],
await_vf: Literal[False] = ...,
await_rf: Literal[True],
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
vf: collections.abc.Callable[[T], collections.abc.Awaitable[V]],
rf: None = ...,
*,
await_kf: Literal[True],
await_vf: Literal[True],
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, types.AsyncGeneratorType[V]]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
vf: collections.abc.Callable[[T], collections.abc.Awaitable[V]],
rf: collections.abc.Callable[[types.AsyncGeneratorType[V]], S],
*,
await_kf: Literal[True],
await_vf: Literal[True],
await_rf: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, S]]
asyncutils.iters.agroupby_transform(
it: asyncutils._internal.prots.SupportsIteration[T],
kf: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
vf: collections.abc.Callable[[T], collections.abc.Awaitable[V]],
rf: collections.abc.Callable[[types.AsyncGeneratorType[V]], collections.abc.Awaitable[S]],
*,
await_kf: Literal[True],
await_vf: Literal[True],
await_rf: Literal[True],
) types.AsyncGeneratorType[tuple[R, S]]

Async version of more_itertools.groupby_transform().

asyncutils.iters.agrouper[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int,
fillvalue: T | asyncutils._internal.prots.Raise = ...,
) types.AsyncGeneratorType[tuple[T | None, Ellipsis]]
Collect items of the (async) iterable it into tuples of length n each.
If fillvalue is RAISE, raise ValueError if the last group is not of length n.
Otherwise, pad the last group with fillvalue to length n if needed. No padding is done if not passed.
async asyncutils.iters.aguessmax[T](
it: asyncutils._internal.prots.SupportsIteration[T],
estlen: int | None = ...,
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison] = ...,
default: T = ...,
finish_event: asyncutils._internal.prots.EventProtocol | None = ...,
reject_cb: None = ...,
) T
async asyncutils.iters.aguessmax(
it: asyncutils._internal.prots.SupportsIteration[T],
estlen: int | None = ...,
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison] = ...,
default: T = ...,
finish_event: asyncutils._internal.prots.EventProtocol | None = ...,
reject_cb: collections.abc.Callable[[T], object],
await_cb: Literal[False] = ...,
) T
async asyncutils.iters.aguessmax(
it: asyncutils._internal.prots.SupportsIteration[T],
estlen: int | None = ...,
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison] = ...,
default: T = ...,
finish_event: asyncutils._internal.prots.EventProtocol | None = ...,
reject_cb: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_cb: Literal[True],
) T

Optimal solution to the secretary problem, using key to guess the maximum item, which is the candidate chosen, with 36.8% accuracy, by finding the maximum among the first 36.8% of the (async) iterable and then returning the first item greater than that afterwards, in O(1) space. reject_cb is called on every rejected candidate once rejected, its return value awaited if await_cb=True is passed, and no more than one candidate is ever stored. This Numberphile video proves that the approach used is best.

async asyncutils.iters.aguessmin[T](
it: asyncutils._internal.prots.SupportsIteration[T],
estlen: int | None = ...,
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison] = ...,
default: T = ...,
finish_event: asyncutils._internal.prots.EventProtocol | None = ...,
reject_cb: None = ...,
) T
async asyncutils.iters.aguessmin(
it: asyncutils._internal.prots.SupportsIteration[T],
estlen: int | None = ...,
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison] = ...,
default: T = ...,
finish_event: asyncutils._internal.prots.EventProtocol | None = ...,
reject_cb: collections.abc.Callable[[T], object],
await_cb: Literal[False] = ...,
) T
async asyncutils.iters.aguessmin(
it: asyncutils._internal.prots.SupportsIteration[T],
estlen: int | None = ...,
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison] = ...,
default: T = ...,
finish_event: asyncutils._internal.prots.EventProtocol | None = ...,
reject_cb: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_cb: Literal[True],
) T

Like aguessmax(), but guesses the minimum item instead.

asyncutils.iters.aichunked[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int,
) types.AsyncGeneratorType[asyncutils.iterclasses.AChain[T]]
asyncutils.iters.aidft(Xarr: asyncutils._internal.prots.SupportsIteration[complex], /) types.AsyncGeneratorType[complex]

The inverse discrete Fourier transform. O(n^2) just like adft().

async asyncutils.iters.aiequals(*its: asyncutils._internal.prots.SupportsIteration[object], strict: bool = ...) bool
async asyncutils.iters.ailen(it: asyncutils._internal.prots.SupportsIteration[object]) int

Return the length of the (async) iterable it, consuming it entirely.

asyncutils.iters.ainterleave_evenly[T](
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
lengths: asyncutils._internal.prots.SupportsIteration[int] | None = ...,
) types.AsyncGeneratorType[T]

Interleave items of the iterables evenly according to the lengths if passed, and determined by calling the __len__() method on the iterables if present otherwise.

asyncutils.iters.ainterleave_randomly[T](
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
) types.AsyncGeneratorType[T]

Interleave items of the iterables randomly, skipping exhausted iterables.

asyncutils.iters.ainterleave_stopearly[T](*it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Yield the items from the iterables in a round-robin fashion until at least one is exhausted.

asyncutils.iters.aintersend[T, R](
i1: collections.abc.AsyncGenerator[T, R],
i2: collections.abc.AsyncGenerator[R, T],
) types.AsyncGeneratorType[tuple[T, R]]

Feed i1 and i2 into each other and yield tuples of the form (yielded_from_i1, yielded_from_i2).

asyncutils.iters.aintersperse[T](e: T, it: asyncutils._internal.prots.SupportsIteration[T], n: int = ...) types.AsyncGeneratorType[T]

Yield e, then the next n items in it, and repeat until it is exhausted.

async asyncutils.iters.aisempty(it: asyncutils._internal.prots.SupportsIteration[object]) bool

Return whether the (async) iterable it is empty.

Note

This advances the iterable on success and discards the item. If the item is needed, call afirst() instead and catch StopAsyncIteration or pass a default value.

asyncutils.iters.aislice[T](
it: asyncutils._internal.prots.SupportsIteration[T],
stop: SupportsIndex | None = ...,
/,
) types.AsyncGeneratorType[T]
asyncutils.iters.aislice(
it: asyncutils._internal.prots.SupportsIteration[T],
start: SupportsIndex | None,
stop: SupportsIndex | None,
step: SupportsIndex | None = ...,
/,
) types.AsyncGeneratorType[T]

Async version of itertools.islice() that is not a class.

async asyncutils.iters.aisprime(n: int) bool

Probabilistically test for primality of n. O(log^3 n), with false-positive rate below 2^(-128) for integers above 10^24.

asyncutils.iters.aiter_idx[T](
it: asyncutils._internal.prots.SupportsIteration[T],
value: T,
start: int = ...,
stop: int | None = ...,
) types.AsyncGeneratorType[int]

Yield the indices at which value occurs in it within start and stop.

asyncutils.iters.aiterate[T](f: collections.abc.Callable[[T], collections.abc.Awaitable[T]], start: T) types.AsyncGeneratorType[T]

Yield start, then the awaited output of f called on the previous output repeatedly.

asyncutils.iters.aiterexcept[T](
f: collections.abc.Callable[[], collections.abc.Awaitable[T]],
exc: asyncutils._internal.prots.CanExcept,
first: collections.abc.Callable[[], collections.abc.Awaitable[T]] = ...,
) types.AsyncGeneratorType[T]

Yield the awaited output of first, then f called with no arguments repeatedly until an exception present in exc occurs.

async asyncutils.iters.alast[T](it: asyncutils._internal.prots.SupportsIteration[T], default: T = ...) T

Return the last item in the (async) iterable it, or default if passed and it is empty.

async asyncutils.iters.all_max[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
default: T = ...,
*,
await_key: Literal[False] = ...,
) list[T]
async asyncutils.iters.all_max(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
default: T = ...,
*,
await_key: Literal[True],
) list[T]
async asyncutils.iters.all_max(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T = ...,
*,
await_key: Literal[False] = ...,
) list[T]
async asyncutils.iters.all_min[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
default: T = ...,
*,
await_key: Literal[False] = ...,
) list[T]
async asyncutils.iters.all_min(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
default: T = ...,
*,
await_key: Literal[True],
) list[T]
async asyncutils.iters.all_min(
it: asyncutils._internal.prots.SupportsIteration[T],
default: T = ...,
*,
await_key: Literal[False] = ...,
) list[T]
asyncutils.iters.aloops(n: int) types.AsyncGeneratorType[None]

Yield None n times. Equivalent to base.take(aforever(), n) and arepeat(None, n), but without creating intermediate integers.

asyncutils.iters.amap[T, R](
f: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_: Literal[True],
strict: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amap(
f: collections.abc.Callable[[T], R],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_: Literal[False] = ...,
strict: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amap(
f: collections.abc.Callable[[T, S], collections.abc.Awaitable[R]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_: Literal[True],
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amap(
f: collections.abc.Callable[[T, S], R],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_: Literal[False] = ...,
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amap(
f: collections.abc.Callable[[T, S, V], collections.abc.Awaitable[R]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_: Literal[True],
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amap(
f: collections.abc.Callable[[T, S, V], R],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_: Literal[False] = ...,
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amap(
f: collections.abc.Callable[[T, S, V, U], collections.abc.Awaitable[R]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_: Literal[True],
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amap(
f: collections.abc.Callable[[T, S, V, U], R],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_: Literal[False] = ...,
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amap(
f: collections.abc.Callable[[*tuple[T, ...]], collections.abc.Awaitable[R]],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[True],
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amap(
f: collections.abc.Callable[[*tuple[T, ...]], R],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[False] = ...,
strict: bool = ...,
) types.AsyncGeneratorType[R]

Async version of map that is not a class, with await_ dictating whether the return value of the function is to be awaited before yielding.

asyncutils.iters.amapif[T, R](
f: collections.abc.Callable[[T], R],
p: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amapif(
f: collections.abc.Callable[[T], R],
p: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_transform: Literal[False],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amapif(
f: collections.abc.Callable[[T], R],
p: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
*,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amapif(
f: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
p: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amapif(
f: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
p: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]

Essentially the restriction of amultimapif() to one (async) iterable.

asyncutils.iters.amatmul[T: (int, float, complex)](
M: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
N: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Matrix multiplication of M and N. O(n^3) time, since this library does not specialize in these operations.

async asyncutils.iters.amatprod[T: asyncutils._internal.prots.SupportsMatMul](it: asyncutils._internal.prots.SupportsIteration[T], start: T) T

Return the product of the matrices in the (async) iterable, preceded by start if passed.

async asyncutils.iters.amax[T: asyncutils._internal.prots.SupportsRichComparison](it: asyncutils._internal.prots.SupportsIteration[T], *, default: T = ...) T
async asyncutils.iters.amax(arg1: T, arg2: T, /, *args: T, default: T = ...) T
async asyncutils.iters.amax(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
default: T = ...,
await_key: Literal[False] = ...,
) T
async asyncutils.iters.amax(
arg1: T,
arg2: T,
/,
*args: T,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
default: T = ...,
await_key: Literal[False] = ...,
) T
async asyncutils.iters.amax(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
default: T = ...,
await_key: Literal[True],
) T
async asyncutils.iters.amax(
arg1: T,
arg2: T,
/,
*args: T,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
default: T = ...,
await_key: Literal[True],
) T

Async version of max().

asyncutils.iters.amerge_sorted_by[T: asyncutils._internal.prots.SupportsRichComparison](
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
*,
key: collections.abc.Callable[[T], T] = ...,
await_: Literal[False] = ...,
reverse: bool = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.amerge_sorted_by(
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
await_: Literal[False] = ...,
reverse: bool = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.amerge_sorted_by(
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
*,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
await_: Literal[True],
reverse: bool = ...,
) types.AsyncGeneratorType[T]

Async version of heapq.merge().

async asyncutils.iters.amin[T: asyncutils._internal.prots.SupportsRichComparison](it: asyncutils._internal.prots.SupportsIteration[T], *, default: T = ...) T
async asyncutils.iters.amin(arg1: T, arg2: T, /, *args: T, default: T = ...) T
async asyncutils.iters.amin(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
default: T = ...,
await_key: Literal[False] = ...,
) T
async asyncutils.iters.amin(
arg1: T,
arg2: T,
/,
*args: T,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
default: T = ...,
await_key: Literal[False] = ...,
) T
async asyncutils.iters.amin(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
default: T = ...,
await_key: Literal[True],
) T
async asyncutils.iters.amin(
arg1: T,
arg2: T,
/,
*args: T,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
default: T = ...,
await_key: Literal[True],
) T

Async version of min().

async asyncutils.iters.aminmax[R](*, default: R) R
async asyncutils.iters.aminmax(it: asyncutils._internal.prots.SupportsIteration[T], /) tuple[T, T]
async asyncutils.iters.aminmax(it: asyncutils._internal.prots.SupportsIteration[T], /, *, default: R) tuple[T, T] | R
async asyncutils.iters.aminmax(a: T, b: T, /, *items: T) tuple[T, T]
async asyncutils.iters.aminmax(a: T, b: T, /, *items: T, default: R) tuple[T, T] | R

Return a tuple of the smallest item and the largest item in the iterable or among the positional arguments by making a single pass. If the iterable is empty, return default. O(1) space and O(n) time.

async asyncutils.iters.aminmax_keyed[R](*, key: collections.abc.Callable[[Any], object], default: R) R
async asyncutils.iters.aminmax_keyed(
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
await_key: Literal[False] = ...,
) tuple[T, T]
async asyncutils.iters.aminmax_keyed(
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
await_key: Literal[False] = ...,
default: R,
) tuple[T, T] | R
async asyncutils.iters.aminmax_keyed(
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
await_key: Literal[True],
) tuple[T, T]
async asyncutils.iters.aminmax_keyed(
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
await_key: Literal[True],
default: R,
) tuple[T, T] | R
async asyncutils.iters.aminmax_keyed(
a: T,
b: T,
/,
*items: T,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
await_key: Literal[False] = ...,
) tuple[T, T]
async asyncutils.iters.aminmax_keyed(
a: T,
b: T,
/,
*items: T,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
await_key: Literal[False] = ...,
default: R,
) tuple[T, T] | R
async asyncutils.iters.aminmax_keyed(
a: T,
b: T,
/,
*items: T,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
await_key: Literal[True],
) tuple[T, T]
async asyncutils.iters.aminmax_keyed(
a: T,
b: T,
/,
*items: T,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
await_key: Literal[True],
default: R,
) tuple[T, T] | R

Like aminmax(), but performs comparisons according to the return value of key.

asyncutils.iters.amultifilter[T](
pred: collections.abc.Callable[[tuple[T]], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, R]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, R, V]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, R, V, U]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, R, V, U, S]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, Ellipsis]], object],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[Any, Ellipsis]], object],
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T]], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, R]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, R, V]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, R, V, U]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, R, V, U, S]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[T, Ellipsis]], collections.abc.Awaitable[object]],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.amultifilter(
pred: collections.abc.Callable[[tuple[Any, Ellipsis]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]

Composition of afilter() and azip().

asyncutils.iters.amultifilterfalse[T](
pred: collections.abc.Callable[[tuple[T]], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, R]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, R, V]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, R, V, U]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, R, V, U, S]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, Ellipsis]], object],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[Any, Ellipsis]], object],
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T]], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, R]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, R, V]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, R, V, U]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, R, V, U, S]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[T, Ellipsis]], collections.abc.Awaitable[object]],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.amultifilterfalse(
pred: collections.abc.Callable[[tuple[Any, Ellipsis]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]

Composition of afilterfalse() and azip().

asyncutils.iters.amultimapif[T, R](
f: collections.abc.Callable[[T], R],
pred: collections.abc.Callable[[tuple[T]], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[T]], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V], R],
pred: collections.abc.Callable[[tuple[T, V]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[T, V]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V, S], R],
pred: collections.abc.Callable[[tuple[T, V, S]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V, S], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[T, V, S]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V, S, U], R],
pred: collections.abc.Callable[[tuple[T, V, S, U]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V, S, U], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[T, V, S, U]], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[*Ts], R],
pred: collections.abc.Callable[[tuple[*Ts]], object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[*Ts], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[*Ts]], object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T], R],
pred: collections.abc.Callable[[tuple[T]], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[T]], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V], R],
pred: collections.abc.Callable[[tuple[T, V]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[T, V]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V, S], R],
pred: collections.abc.Callable[[tuple[T, V, S]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V, S], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[T, V, S]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V, S, U], R],
pred: collections.abc.Callable[[tuple[T, V, S, U]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[T, V, S, U], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[T, V, S, U]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[*Ts], R],
pred: collections.abc.Callable[[tuple[*Ts]], collections.abc.Awaitable[object]],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultimapif(
f: collections.abc.Callable[[*Ts], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[tuple[*Ts]], collections.abc.Awaitable[object]],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]

Composition of astarmap(), afilter() and azip().

asyncutils.iters.amultistarfilter[T](
pred: collections.abc.Callable[[T], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[T, R], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[T, R, V], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[T, R, V, U], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[T, R, V, U, S], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[*tuple[T, ...]], object],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[*tuple[Any, ...]], object],
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[T, R], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[T, R, V], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[T, R, V, U], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[T, R, V, U, S], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[*tuple[T, ...]], collections.abc.Awaitable[object]],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.amultistarfilter(
pred: collections.abc.Callable[[*tuple[Any, ...]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]

Composition of astarfilter() and azip().

asyncutils.iters.amultistarfilterfalse[T](
pred: collections.abc.Callable[[T], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[T, R], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[T, R, V], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[T, R, V, U], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[T, R, V, U, S], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[*tuple[T, ...]], object],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[*tuple[Any, ...]], object],
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
strict: bool = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[T, R], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[T, R, V], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[T, R, V, U], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[T, R, V, U, S], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[*tuple[T, ...]], collections.abc.Awaitable[object]],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.amultistarfilterfalse(
pred: collections.abc.Callable[[*tuple[Any, ...]], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
strict: bool = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]

Composition of astarfilterfalse() and azip().

asyncutils.iters.amultistarmapif[T, R](
f: collections.abc.Callable[[T], R],
pred: collections.abc.Callable[[T], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[T], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V], R],
pred: collections.abc.Callable[[T, V], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[T, V], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V, S], R],
pred: collections.abc.Callable[[T, V, S], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V, S], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[T, V, S], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V, S, U], R],
pred: collections.abc.Callable[[T, V, S, U], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V, S, U], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[T, V, S, U], object],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[*Ts], R],
pred: collections.abc.Callable[[*Ts], object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
await_transform: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[*Ts], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[*Ts], object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
await_transform: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T], R],
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V], R],
pred: collections.abc.Callable[[T, V], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[T, V], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V, S], R],
pred: collections.abc.Callable[[T, V, S], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V, S], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[T, V, S], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V, S, U], R],
pred: collections.abc.Callable[[T, V, S, U], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[T, V, S, U], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[T, V, S, U], collections.abc.Awaitable[object]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[S],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[*Ts], R],
pred: collections.abc.Callable[[*Ts], collections.abc.Awaitable[object]],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
await_transform: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.amultistarmapif(
f: collections.abc.Callable[[*Ts], collections.abc.Awaitable[R]],
pred: collections.abc.Callable[[*Ts], collections.abc.Awaitable[object]],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
await_transform: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]

Composition of astarmap() and amultistarfilter().

asyncutils.iters.ancycles[T](it: asyncutils._internal.prots.SupportsIteration[T], n: int) types.AsyncGeneratorType[T]

Yield the items in the (async) iterable it over and over for a total of n cycles.

async asyncutils.iters.anth[T](it: asyncutils._internal.prots.SupportsIteration[T], n: int, default: T = ...) T

Return the n-th item of the (async) iterable it, or default if passed and there is no such item.

asyncutils.iters.anth_combination[T](it: asyncutils._internal.prots.SupportsIteration[T], r: int, n: int) types.AsyncGeneratorType[T]

Return the n-th combination of r elements from the input iterable it, in lexicographic order.

async asyncutils.iters.anth_combination_with_replacement[T](
it: asyncutils._internal.prots.SupportsIteration[T],
r: int,
n: int,
) tuple[T, Ellipsis]

Return the n-th combination of r elements from the input iterable it, in lexicographic order, allowing individual elements to be repeated.

async asyncutils.iters.anth_or_last[T](it: asyncutils._internal.prots.SupportsIteration[T], n: int, default: T = ...) T

Return the n-th item in the (async) iterable it, or the last item if out of bounds, or default if passed and it is empty.

async asyncutils.iters.anth_permutation[T](it: asyncutils._internal.prots.SupportsIteration[T], r: int, n: int) tuple[T, Ellipsis]

Return the n-th permutation of r elements from the input iterable it, in lexicographic order.

async asyncutils.iters.anth_product[T](n: int, *its: asyncutils._internal.prots.SupportsIteration[T], repeat: int = ...) tuple[T, Ellipsis]

Return the n-th item of the Cartesian product of the input iterables its, in lexicographic order, with each iterable repeated repeat times.

asyncutils.iters.aonline_sorter[T: asyncutils._internal.prots.NotNone](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
reverse: bool = ...,
*,
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[T, T | None]
asyncutils.iters.aonline_sorter(
it: asyncutils._internal.prots.SupportsIteration[T],
key: None = ...,
reverse: bool = ...,
*,
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[T, T | None]
asyncutils.iters.aonline_sorter(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
reverse: bool = ...,
*,
await_key: Literal[True],
) types.AsyncGeneratorType[T, T | None]
Sort items from an (async) iterable and those sent in on the fly in the async generator interface (i.e. by awaiting the return value of asend).
If reverse is True, emit items in descending order.
The return value of key is awaited iff await_key=True is passed. If key is None (the default), the items themselves are compared.
Items cannot be None, because for an async generator agen, agen.asend(None) and anext(agen) are indistinguishable.
If it is empty, the generator will also be empty.

Note

Uses a heap internally, which is O(log n) time per item. Requires O(n) preprocessing time and O(n) auxiliary space.

Note

This function will instantiate and subsequently reuse an executor if there are 131072 initial items or more.

asyncutils.iters.aouter_product[T, R, V, **P](
f: collections.abc.Callable[Concatenate[T, R, P], collections.abc.Awaitable[V]],
xs: asyncutils._internal.prots.SupportsIteration[T],
ys: asyncutils._internal.prots.SupportsIteration[R],
/,
*a: P,
**k: P,
) types.AsyncGeneratorType[list[V]]
asyncutils.iters.apadded[T](
it: asyncutils._internal.prots.SupportsIteration[T],
fillvalue: T,
n: int | None = ...,
) types.AsyncGeneratorType[T]

Yield the items in the (async) iterable it, followed by fillvalue repeatedly, such that the iterable is fully consumed and the result has length at least n if passed.

asyncutils.iters.apadnone[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int | None = ...,
) types.AsyncGeneratorType[T | None]

Yield the items in the (async) iterable it, followed by None repeatedly, such that the iterable is fully consumed and the result has length at least n if passed.

asyncutils.iters.apairwise[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[tuple[T, T]]

Async version of itertools.pairwise() that is not a class.

asyncutils.iters.apartition[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]

Return a tuple (fg, tg). tg is an async generator yielding the items in it passing the predicate, and fg the others.

asyncutils.iters.apermutations[T](
it: asyncutils._internal.prots.SupportsIteration[T],
r: int | None = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Async version of itertools.permutations() that is not a class.

asyncutils.iters.apolynomial_derivative[T: (int, float, complex)](coeff: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Compute the coefficients of the derivative of a polynomial. Both input and output iterables are in order of descending powers.

async asyncutils.iters.apolynomial_eval[T: (int, float, complex)](coeff: asyncutils._internal.prots.SupportsIteration[T], x: T) T

Evaluate a polynomial at x given its coefficients in order of descending powers.

asyncutils.iters.apolynomial_from_roots[T: (int, float, complex)](roots: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Generate the coefficients of a polynomial given its roots in order of descending powers.

asyncutils.iters.apowers[T: (int, float, complex)](base: T, start: T = ...) types.AsyncGeneratorType[T]

Yield start, start*base, start*base*base, …

Note

When it is found that the base is a perfect power of two, this will delegate to apowers_of_two() as an optimization.

asyncutils.iters.apowers_of_two(*, init: int = ..., init_shift: int = ..., shift: int = ...) types.AsyncGeneratorType[int]

Optimized version of apowers() using bit shift operations for powers of two, four, eight, etc. Yield init<<init_shift, init<<init_shift+shift, init<<init_shift+2*shift, …

asyncutils.iters.apowerset[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Yield all the subsets of the (async) iterable it (by index!) as tuples, starting with the empty tuple.

asyncutils.iters.apowerset_of_sets[T: collections.abc.Hashable](
it: asyncutils._internal.prots.SupportsIteration[T],
*,
frozen: Literal[True] = ...,
) types.AsyncGeneratorType[frozenset[T]]
asyncutils.iters.apowerset_of_sets(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
frozen: Literal[False],
) types.AsyncGeneratorType[set[T]]

Yield all the subsets of the items in the (async) iterable of hashable objects after consuming it at once and removing duplicates, as frozenset’s if frozen is True (the default) and set’s otherwise.

asyncutils.iters.aprepend[T](val: T, it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Prepend val to the (async) iterable it.

async asyncutils.iters.aprod[T: (int, float, complex)](it: asyncutils._internal.prots.SupportsIteration[T], start: T = ...) T

Return the product of the items in the (async) iterable, preceded by start if passed.

asyncutils.iters.aproduct[T](
i1: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R, Ellipsis]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R | V, Ellipsis]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R | V | U, Ellipsis]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R | V | U | S, Ellipsis]]
asyncutils.iters.aproduct(
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
repeat: int = ...,
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]
asyncutils.iters.aproduct(
*its: asyncutils._internal.prots.SupportsIteration[T],
repeat: int = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Async version of itertools.product() that is not a class.

async asyncutils.iters.aquantify[T](
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], object] = ...,
) int

Return the number of items in the (async) iterable for which the predicate is true.

asyncutils.iters.arandom_combination[T](it: asyncutils._internal.prots.SupportsIteration[T], r: int) types.AsyncGeneratorType[T]

Draw r items at random from the input iterable it, without replacement.

asyncutils.iters.arandom_combination_with_replacement[T](
it: asyncutils._internal.prots.SupportsIteration[T],
r: int,
) types.AsyncGeneratorType[T]

Draw r items at random from the input iterable it, with replacement.

async asyncutils.iters.arandom_derangement[T](it: asyncutils._internal.prots.SupportsIteration[T]) tuple[T, Ellipsis]

Generate a random derangement of items in the (async) iterable it.

asyncutils.iters.arandom_permutation[T](
it: asyncutils._internal.prots.SupportsIteration[T],
r: int | None = ...,
) types.AsyncGeneratorType[T]

Choose a random permutation of the elements in it of size r, or all sizes if not passed.

asyncutils.iters.arandom_product[T](*its: asyncutils._internal.prots.SupportsIteration[T], n: int = ...) types.AsyncGeneratorType[T]

Draw n items from each of the input iterables its at random.

asyncutils.iters.arange(stop: int, /) types.AsyncGeneratorType[int]
asyncutils.iters.arange(start: int, stop: int, step: int = ..., /) types.AsyncGeneratorType[int]

Async version of range that is not a class.

asyncutils.iters.arepeat[T](elem: T, n: int = ...) types.AsyncGeneratorType[T]

Async version of itertools.repeat() that is not a class.

asyncutils.iters.arepeat_each[T](it: asyncutils._internal.prots.SupportsIteration[T], n: int) types.AsyncGeneratorType[T]

Yield each item in the (async) iterable it exactly n times before advancing.

asyncutils.iters.arepeat_func[T, *Ts](
f: collections.abc.Callable[[*Ts], collections.abc.Awaitable[T]],
times: int | None = ...,
*a: *Ts,
) types.AsyncGeneratorType[T]

Call the async function f with arguments a repeatedly for times times, or indefinitely if times is not passed, and yield the results awaited.

asyncutils.iters.arepeat_last[T](
it: asyncutils._internal.prots.SupportsIteration[T],
default: T | asyncutils._internal.prots.Raise = ...,
) types.AsyncGeneratorType[T]

Yield all the items in the (async) iterable it, then keep yielding the last item forever, or default if the iterable was empty, stopping if it was not passed. If default was RAISE, raise ItemsExhausted.

asyncutils.iters.areshape[T](
mat: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
shape: int,
) types.AsyncGeneratorType[list[T]]
asyncutils.iters.areshape(
mat: asyncutils._internal.prots.SupportsIteration[object],
shape: asyncutils._internal.prots.SupportsIteration[int],
) types.AsyncGeneratorType[list[Any]]

Change the shape of a tensor according to shape. For an integer shape, the matrix must be 2D and shape is the number of output columns.

asyncutils.iters.areversed[T](
it: asyncutils._internal.prots.SupportsIteration[T] | collections.abc.Reversible[T],
/,
) types.AsyncGeneratorType[T]

Reverse an (async) iterable, calling its __reversed__() method and converting the result into an async generator if present, and fall back to consuming and saving all the items and yielding them in reverse order.

asyncutils.iters.aroundrobin[T](*its: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Yield items from the given (async) iterables in round-robin order, skipping exhausted iterables. Prefer over aroundrobin2() for less iterables.

asyncutils.iters.aroundrobin2[T](*its: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Yield items from the given (async) iterables in round-robin order, skipping exhausted iterables. Prefer over aroundrobin() for more iterables.

asyncutils.iters.arunlength_decode[T](it: asyncutils._internal.prots.SupportsIteration[tuple[T, int]], /) types.AsyncGeneratorType[T]

Inverse of the above, but takes any (async) iterable and always gives an async generator.

asyncutils.iters.arunlength_encode[T](it: asyncutils._internal.prots.SupportsIteration[T], /) types.AsyncGeneratorType[tuple[T, int]]

Compress an (async) iterable into an async generator of pairs with run-length encoding. Items in the result are in the form (item, count), where item is an item from the input iterable and count is the number of times it is repeated consecutively.

asyncutils.iters.arunning_mean[T: (int, float, complex)](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Repeatedly yield the mean of the items in the iterable so far, and advance the iterable.

asyncutils.iters.arunning_median[T: (int, float)](
it: asyncutils._internal.prots.SupportsIteration[T],
*,
maxlen: SupportsIndex | None = ...,
) types.AsyncGeneratorType[T]

Yield the median of all the items seen from it within a window of size maxlen, then advance it.

async asyncutils.iters.asample_l[T](
it: asyncutils._internal.prots.SupportsIteration[T],
k: int,
*,
rrange: collections.abc.Callable[[int], int] = ...,
rand: collections.abc.Callable[[], float] = ...,
) list[T]

Chooses k items from an (async) iterable of items, where each item is chosen with equal probability. rrange and rand should be the randrange() and random() methods of a random device respectively. This is Algorithm L.

async asyncutils.iters.asample_weighted[T](
it: asyncutils._internal.prots.SupportsIteration[tuple[T, float]],
k: int,
*,
rrange: collections.abc.Callable[[int], int] = ...,
rand: collections.abc.Callable[[], float] = ...,
) list[T]

Choose k items from an (async) iterable of (item, weight) pairs, where the probability of each item being chosen is proportional to its weight. rrange and rand should be the randrange() and random() methods of a random device respectively. This is the A-Chao with Jumps reservoir sampling algorithm.

async asyncutils.iters.asattolo[T](it: asyncutils._internal.prots.SupportsIteration[T], /) list[T]

Return a list representing a random full-length permutation of the items in it.

asyncutils.iters.asendstream[T, R](
i1: collections.abc.AsyncGenerator[T, R],
i2: asyncutils._internal.prots.SupportsIteration[R],
) types.AsyncGeneratorType[T]

Feed i2 into i1 and yield the results.

asyncutils.iters.aserialize[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Protect an (async) iterable from being consumed by many parties concurrently by applying an async lock.

asyncutils.iters.aside_effect[T](
f: collections.abc.Callable[[list[T]], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
size: int,
before: collections.abc.Callable[[], object] | None = ...,
after: collections.abc.Callable[[], object] | None = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.aside_effect(
f: collections.abc.Callable[[T], object],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
size: None = ...,
before: collections.abc.Callable[[], object] | None = ...,
after: collections.abc.Callable[[], object] | None = ...,
) types.AsyncGeneratorType[T]
Apply a side effect function f to each item in an (async) iterable it and yield the items unchanged in an async generator.
If size is specified, the side effect function is applied to batches of that size instead of individual items, but the items are still yielded separately.
The before and after functions are called before and after the iteration, respectively, but after is not called if before fails.
asyncutils.iters.asieve(n: int) types.AsyncGeneratorType[int]

Yield prime numbers strictly smaller than n in order in an async generator.

asyncutils.iters.asliced[T: asyncutils._internal.prots.SupportsSlicing[Any]](seq: T, n: int, strict: bool = ...) types.AsyncGeneratorType[T]
Slice a sliceable object seq (so named because these are usually sequences) and yield slices of the size n, which should be of the same type as seq, from the start to the end.
If strict is True, raise ValueError if the length of any slice is less than n (should only happen for the last slice unless the __getitem__() method is implemented incorrectly).
asyncutils.iters.asorted[T: asyncutils._internal.prots.SupportsRichComparison](it: asyncutils._internal.prots.SupportsIteration[T], *, reverse: bool = ...) list[T]
asyncutils.iters.asorted(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
reverse: bool = ...,
await_key: Literal[False] = ...,
) list[T]
asyncutils.iters.asorted(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
reverse: bool = ...,
await_key: Literal[True],
) list[T]

Async version of sorted(). O(n log n) time and O(n) space, but nowhere near as optimized as the builtin version.

asyncutils.iters.asplitat[T](
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], object],
maxsplit: int = ...,
keep_sep: bool = ...,
) types.AsyncGeneratorType[list[T]]

Split an async iterator at each item satisfying pred, with keep_sep dictating whether the separator is to be included as the last item of each list.

asyncutils.iters.aspy[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int = ...,
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]

Return an async generator containing the first n items, and another containing all the original items.

asyncutils.iters.astarfilter[T](
pred: collections.abc.Callable[[*tuple[T, ...]], object],
it: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.astarfilter(
pred: collections.abc.Callable[[*tuple[T, ...]], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Filter an (async) iterable of tuples of items, yielding only those tuples for which the predicate returns a truthy value when called on the tuple unpacked.

asyncutils.iters.astarfilterfalse[T](
pred: collections.abc.Callable[[*tuple[T, ...]], object],
it: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.astarfilterfalse(
pred: collections.abc.Callable[[*tuple[T, ...]], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
await_pred: Literal[True],
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Filter an (async) iterable of tuples of items, yielding only those tuples for which the predicate returns a falsy value when called on the tuple unpacked.

asyncutils.iters.astarmap[*Ts, R](
f: collections.abc.Callable[[*Ts], R],
it: asyncutils._internal.prots.SupportsIteration[tuple[*Ts]],
/,
await_: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.astarmap(
f: collections.abc.Callable[[*Ts], collections.abc.Awaitable[R]],
it: asyncutils._internal.prots.SupportsIteration[tuple[*Ts]],
/,
await_: Literal[True],
) types.AsyncGeneratorType[R]

Async version of itertools.starmap() that is not a class. await_ specifies whether to await the return value of the transformation function.

asyncutils.iters.astarmap_with_kwds[T](
f: collections.abc.Callable[Ellipsis, T],
it: asyncutils._internal.prots.SupportsIteration[tuple[collections.abc.Iterable[Any], collections.abc.Mapping[str, Any]]],
/,
) types.AsyncGeneratorType[T]

Like amap(), but the iterable should yield tuples of the form (args, kwargs), where args is an iterable of positional arguments and kwargs is a mapping of keyword arguments.

asyncutils.iters.asubslices[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[tuple[T, Ellipsis]]

asubstrings(), but yield all subslices containing the first item first in ascending order of length, then all subslices containing the second item but not the first, and so on.

asyncutils.iters.asubstr_indices[S: (str, bytes, bytearray)](seq: S, reverse: bool = ...) types.AsyncGeneratorType[tuple[S, int, int]]
asyncutils.iters.asubstr_indices(
seq: asyncutils._internal.prots.SupportsSlicing[T],
reverse: bool = ...,
) types.AsyncGeneratorType[tuple[collections.abc.Iterable[T], int, int]]

Yield tuples of the form (substr, start, end), where substr is a contiguous subsequence of seq starting at index start and ending at index end-1 (such that its length is end-start).

asyncutils.iters.asubstrings[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Yield all contiguous subsequences of the (async) iterable it as tuples, in increasing order of length.

See also

asubslices() does the same in a different order.

async asyncutils.iters.asum[T: (int, float, complex)](it: asyncutils._internal.prots.SupportsIteration[T], start: T = ...) T

Return the sum of the items in the (async) iterable, preceded by start if passed.

async asyncutils.iters.asum_of_squares[T: (int, float, complex)](it: asyncutils._internal.prots.SupportsIteration[T]) T

Return the sum of squares of items in an (async) iterable of numbers as a number of the same type.

async asyncutils.iters.asumprod[T: (int, float, complex)](
p: asyncutils._internal.prots.SupportsIteration[T],
q: asyncutils._internal.prots.SupportsIteration[T],
/,
) T

Return the sum of products of items in two iterables of numbers as a number of the same type. Not as precise as math.sumprod() for floating-point numbers, but supports async iterables.

async asyncutils.iters.at_most_one[T](it: asyncutils._internal.prots.SupportsIteration[T], default: None = ...) T | None
async asyncutils.iters.at_most_one(it: asyncutils._internal.prots.SupportsIteration[T], default: R) T | R
asyncutils.iters.atabulate[T](
f: collections.abc.Callable[[int], T],
start: int = ...,
step: int = ...,
/,
*,
await_: Literal[False],
) types.AsyncGeneratorType[T]
asyncutils.iters.atabulate(
f: collections.abc.Callable[[int], collections.abc.Awaitable[T]],
start: int = ...,
step: int = ...,
/,
*,
await_: Literal[True] = ...,
) types.AsyncGeneratorType[T]

Composition of amap() and acount().

asyncutils.iters.atabulate_finite[T](
f: collections.abc.Callable[[int], collections.abc.Awaitable[T]],
stop: int,
/,
*,
await_: Literal[True] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.atabulate_finite(
f: collections.abc.Callable[[int], collections.abc.Awaitable[T]],
start: int,
stop: int,
step: int = ...,
/,
*,
await_: Literal[True] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.atabulate_finite(
f: collections.abc.Callable[[int], T],
stop: int,
/,
*,
await_: Literal[False],
) types.AsyncGeneratorType[T]
asyncutils.iters.atabulate_finite(
f: collections.abc.Callable[[int], T],
start: int,
stop: int,
step: int = ...,
/,
*,
await_: Literal[False],
) types.AsyncGeneratorType[T]
asyncutils.iters.atail[T](n: int, it: asyncutils._internal.prots.SupportsIteration[T], /) types.AsyncGeneratorType[T]

Yield the last n items from the (async) iterable it.

asyncutils.iters.atakeuntil[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.atakeuntil(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]

Take items from the iterable until the predicate called on the item holds.

asyncutils.iters.atakeuntil_inclusive[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.atakeuntil_inclusive(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]

Like atakewhile() but stops only after yielding the first truthy item.

asyncutils.iters.atakewhile[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.atakewhile(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]

Async version of itertools.takewhile() that is not a class.

asyncutils.iters.atakewhile_inclusive[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.atakewhile_inclusive(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]

Like atakewhile() but stops only after yielding the first falsy item.

asyncutils.iters.atranspose[T](
mat: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Compute the transpose of a matrix.

asyncutils.iters.atriplewise[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[tuple[T, T, T]]

Yield overlapping triples of items from an (async) iterable.

asyncutils.iters.aunique[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison] | None = ...,
reverse: bool = ...,
) types.AsyncGeneratorType[T]

Yield unique elements from it in sorted order, according to key, which should not be too expensive. If reverse is True, yield in descending order.

asyncutils.iters.aunique_everseen[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]
asyncutils.iters.aunique_everseen(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_key: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.aunique_everseen(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], object],
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[T]

Yield items from the (async) iterable it, without yielding items already previously yielded.

asyncutils.iters.aunique_justseen[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]
asyncutils.iters.aunique_justseen(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_key: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.aunique_justseen(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], object],
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[T]

Yield items from the (async) iterable it, without yielding consecutive duplicate items.

asyncutils.iters.aunique_to_each[T: collections.abc.Hashable](*its: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Given multiple (async) iterables, yield every item that is only seen in exactly one of the iterables.

async asyncutils.iters.aunzip[T](
ait: asyncutils._internal.prots.SupportsIteration[tuple[T]],
*,
put_batch: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T]]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[T | R]],
*,
put_batch: int = ...,
fillvalue: R,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T]]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[T, S]],
*,
put_batch: int = ...,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T], asyncutils._internal.prots.AUnzipConsumer[S]]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[T | R, S | R]],
*,
put_batch: int = ...,
fillvalue: R,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T], asyncutils._internal.prots.AUnzipConsumer[S]]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[T, S, V]],
*,
put_batch: int = ...,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T], asyncutils._internal.prots.AUnzipConsumer[S], asyncutils._internal.prots.AUnzipConsumer[V]]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[T | R, S | R, V | R]],
*,
put_batch: int = ...,
fillvalue: R,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T], asyncutils._internal.prots.AUnzipConsumer[S], asyncutils._internal.prots.AUnzipConsumer[V]]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[T, S, V, U]],
*,
put_batch: int = ...,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T], asyncutils._internal.prots.AUnzipConsumer[S], asyncutils._internal.prots.AUnzipConsumer[V], asyncutils._internal.prots.AUnzipConsumer[U]]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[T | R, S | R, V | R, U | R]],
*,
put_batch: int = ...,
fillvalue: R,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T], asyncutils._internal.prots.AUnzipConsumer[S], asyncutils._internal.prots.AUnzipConsumer[V], asyncutils._internal.prots.AUnzipConsumer[U]]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[T, Ellipsis]],
*,
put_batch: int = ...,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T], Ellipsis]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[T | R, Ellipsis]],
*,
put_batch: int = ...,
fillvalue: R,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[T], Ellipsis]
async asyncutils.iters.aunzip(
ait: asyncutils._internal.prots.SupportsIteration[tuple[Any, Ellipsis]],
*,
put_batch: int = ...,
fillvalue: object = ...,
maxqsize: int = ...,
) tuple[asyncutils._internal.prots.AUnzipConsumer[Any], Ellipsis]
Undo the effect of zip, itertools.zip_longest(), aziplongest() or azip().
This function operates lazily, consuming items from the async iterable only when needed, in batches of size put_batch (default AUNZIP_DEFAULT_PUT_BATCH) and caching other items in queues of capacity maxqsize (default AUNZIP_DEFAULT_MAX_QSIZE).

Warning

This function may require significant auxiliary space.

asyncutils.iters.awindowed_complete[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int,
) types.AsyncGeneratorType[tuple[tuple[T, Ellipsis], tuple[T, Ellipsis], tuple[T, Ellipsis]]]

Yield tuples of the form (prev, window, next), where window is a tuple of n items from the (async) iterable it, and prev and next are tuples of all the items before and after that window, respectively. Consumes and caches the whole iterable, so use with caution.

asyncutils.iters.awrap[T](it: asyncutils._internal.prots.SupportsIteration[T], start: T, end: T) types.AsyncGeneratorType[T]

Wrap the (async) iterable it by yielding start first, then the items in it, then end.

asyncutils.iters.awrapf[T](
it: asyncutils._internal.prots.SupportsIteration[T],
before: collections.abc.Callable[[], object],
after: None = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.awrapf(
it: asyncutils._internal.prots.SupportsIteration[T],
before: None,
after: collections.abc.Callable[[], object],
) types.AsyncGeneratorType[T]
asyncutils.iters.awrapf(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
after: collections.abc.Callable[[], object],
) types.AsyncGeneratorType[T]
asyncutils.iters.awrapf(
it: asyncutils._internal.prots.SupportsIteration[T],
before: collections.abc.Callable[[], object],
after: collections.abc.Callable[[], object],
) types.AsyncGeneratorType[T]

Call before when the iterable starts, then yield the items in it, then call after as long as before did not raise and the iterable was converted to an async generator successfully. The return value of each function is awaited if it doesn’t raise TypeError.

asyncutils.iters.azip[T](i1: asyncutils._internal.prots.SupportsIteration[T], /) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.azip(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.azip(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
strict: Literal[True],
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.azip(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.azip(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
strict: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.azip(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.azip(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
strict: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.azip(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.azip(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
strict: Literal[True],
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.azip(
*its: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Async version of zip that is not a class.

asyncutils.iters.azip_offset[T](
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None]]
asyncutils.iters.azip_offset(
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: R,
) types.AsyncGeneratorType[tuple[T | R]]
asyncutils.iters.azip_offset(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, R | None]]
asyncutils.iters.azip_offset(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: V,
) types.AsyncGeneratorType[tuple[T | V, R | V]]
asyncutils.iters.azip_offset(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, R | None, V | None]]
asyncutils.iters.azip_offset(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: U,
) types.AsyncGeneratorType[tuple[T | U, R | U, V | U]]
asyncutils.iters.azip_offset(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, R | None, V | None, U | None]]
asyncutils.iters.azip_offset(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: S,
) types.AsyncGeneratorType[tuple[T | S, R | S, V | S, U | S]]
asyncutils.iters.azip_offset(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, R | None, V | None, U | None, S | None]]
asyncutils.iters.azip_offset(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[T],
i3: asyncutils._internal.prots.SupportsIteration[T],
i4: asyncutils._internal.prots.SupportsIteration[T],
i5: asyncutils._internal.prots.SupportsIteration[T],
i6: asyncutils._internal.prots.SupportsIteration[T],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, Ellipsis]]
asyncutils.iters.azip_offset(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[T],
i3: asyncutils._internal.prots.SupportsIteration[T],
i4: asyncutils._internal.prots.SupportsIteration[T],
i5: asyncutils._internal.prots.SupportsIteration[T],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
longest: bool = ...,
fillvalue: R,
) types.AsyncGeneratorType[tuple[T | R, Ellipsis]]
asyncutils.iters.aziplongest[T](i1: asyncutils._internal.prots.SupportsIteration[T], /) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.aziplongest(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
fillvalue: object = ...,
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.aziplongest(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
fillvalue: object = ...,
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.aziplongest(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
fillvalue: object = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.aziplongest(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
fillvalue: object = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.aziplongest(
*its: asyncutils._internal.prots.SupportsIteration[T],
fillvalue: T = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]

Async version of itertools.zip_longest() that is not a class. The first overload does not accept fillvalue, because passing it with only one iterable does not make sense.

async asyncutils.iters.basic_collect[T](it: asyncutils._internal.prots.SupportsIteration[T], n: int = ...) list[T]

Return a list of the first n items in the (async) iterable it, signalling no error if there are not enough items.

asyncutils.iters.batch[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int,
*,
item_timeout: float | None = ...,
strict: bool = ...,
) types.AsyncGeneratorType[list[T]]

More flexible but slightly slower implementation of batch2(), supporting timeouts waiting for each item, that raises ValueError instead of ItemsExhausted in the case of the length of the iterable being indivisible by the batch size.

asyncutils.iters.batch2[T](
it: asyncutils._internal.prots.SupportsIteration[T],
n: int,
strict: Literal[True],
) types.AsyncGeneratorType[list[T]]
asyncutils.iters.batch2(
it: asyncutils._internal.prots.SupportsIteration[T],
n: int | None,
strict: Literal[False] = ...,
) types.AsyncGeneratorType[list[T]]

Batch an (async) iterable into an async generator of lists. If strict=True is specified, raise ItemsExhausted on the last batch if it is discovered then that the iterable does not have enough items for a complete batch.

asyncutils.iters.batch_process[T, R](
items: asyncutils._internal.prots.SupportsIteration[T],
size: int,
processor: collections.abc.Callable[[list[T]], collections.abc.Awaitable[R]],
) types.AsyncGeneratorType[R]

Apply processor to each batch of size size in items and yield the results awaited.

asyncutils.iters.buffer[T](
it: asyncutils._internal.prots.SupportsIteration[T],
maxsize: int = ...,
*,
timeout_get: float | None = ...,
timeout_put: float | None = ...,
cooldown: float = ...,
) types.AsyncGeneratorType[T]
Buffer the given (async) iterable in an async generator, with an async queue as buffer of capacity maxsize (default unbounded) and optional timeouts for getting and putting items into the buffer.
cooldown specifies how long to wait after hitting a get timeout before trying again; whereas when a put timeout is reached, the async generator finishes.
asyncutils.iters.circular_shifts[T](
it: asyncutils._internal.prots.SupportsIteration[T],
steps: int = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.cloned[T: asyncutils._internal.prots.SupportsCopy](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]

Yield copies of the items in the (async) iterable it, as returned by copy().

asyncutils.iters.coalesce[T](
it: asyncutils._internal.prots.SupportsIteration[T],
f: collections.abc.Callable[[T, T], T | asyncutils._internal.prots.NoCoalesce],
await_: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.coalesce(
it: asyncutils._internal.prots.SupportsIteration[T],
f: collections.abc.Callable[[T, T], collections.abc.Awaitable[T | asyncutils._internal.prots.NoCoalesce]],
await_: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.counts[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: None = ...,
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[asyncutils._internal.prots.CountItem[T, T]]
asyncutils.iters.counts(
it: asyncutils._internal.prots.SupportsIteration[T],
key: None = ...,
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[asyncutils._internal.prots.CountItem[T, T]]
asyncutils.iters.counts(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], R],
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[asyncutils._internal.prots.CountItem[T, R]]
asyncutils.iters.counts(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
await_key: Literal[True],
) types.AsyncGeneratorType[asyncutils._internal.prots.CountItem[T, R]]
asyncutils.iters.decreasing_runs[T: asyncutils._internal.prots.SupportsRichComparison](
it: asyncutils._internal.prots.SupportsIteration[T],
typ: type[T] | None = ...,
max_runs: int = ...,
) types.AsyncGeneratorType[list[T]]
async asyncutils.iters.diff_with[T, R](
it1: asyncutils._internal.prots.SupportsIteration[T],
it2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
cmpeq: collections.abc.Callable[[T, R], object] = ...,
) FirstMisMatch[T, R] | Shorter[T] | Longer[R] | None
asyncutils.iters.distribute[T](n: Literal[1], it: asyncutils._internal.prots.SupportsIteration[T]) tuple[types.AsyncGeneratorType[T]]
asyncutils.iters.distribute(
n: Literal[2],
it: asyncutils._internal.prots.SupportsIteration[T],
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]
asyncutils.iters.distribute(
n: Literal[3],
it: asyncutils._internal.prots.SupportsIteration[T],
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]
asyncutils.iters.distribute(
n: Literal[4],
it: asyncutils._internal.prots.SupportsIteration[T],
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]
asyncutils.iters.distribute(
n: Literal[5],
it: asyncutils._internal.prots.SupportsIteration[T],
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]
asyncutils.iters.distribute(n: int, it: asyncutils._internal.prots.SupportsIteration[T]) tuple[types.AsyncGeneratorType[T], Ellipsis]
asyncutils.iters.duplicates[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: None = ...,
*,
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.duplicates(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Hashable],
*,
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.duplicates(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[collections.abc.Hashable]],
*,
await_key: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.empty_agen() types.AsyncGeneratorType[Never]

Return an async generator that yields nothing. Due to async generator finalization issues, this is not a constant like yield_to_event_loop.

asyncutils.iters.extract[T](
it: asyncutils._internal.prots.SupportsIteration[T],
indices: asyncutils._internal.prots.SupportsIteration[SupportsIndex],
fut: asyncio.Future[float] | None = ...,
finish: bool = ...,
) list[asyncio.Future[T]]
Take an (async) iterable and an (async) iterable of integers interpreted as indices, and immediately returns a list of futures.
Their eventual results represent the items of that iterable at the corresponding index.
Also begin consumption of the iterable in the background.
Exceptions will be set in the futures that are not done if results are encountered during iteration or if the index is out of bounds.
Pass in a Future for the fut parameter, which cancels the background consumption of the async iterable once it is done and cancels the undone futures.

Attention

Negative indices would consume the whole iterable at once if not already consumed.

Warning

Do not set the result of any returned future; instead, if the result is no longer relevant, cancel the future.

Note

The consumption stops as soon as all the required results are pushed into the respective futures.

asyncutils.iters.extract_monotonic[T](
it: asyncutils._internal.prots.SupportsIteration[T],
indices: asyncutils._internal.prots.SupportsIteration[SupportsIndex],
) types.AsyncGeneratorType[T]
asyncutils.iters.filter_identical[T](it: asyncutils._internal.prots.SupportsIteration[T], s: T) types.AsyncGeneratorType[T]
asyncutils.iters.flat_map[T, R](
f: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsIteration[R]]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_: Literal[True],
strict: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.flat_map(
f: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsIteration[R]],
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_: Literal[False] = ...,
strict: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.flat_map(
f: collections.abc.Callable[[T, S], collections.abc.Awaitable[asyncutils._internal.prots.SupportsIteration[R]]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_: Literal[True],
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.flat_map(
f: collections.abc.Callable[[T, S], asyncutils._internal.prots.SupportsIteration[R]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_: Literal[False] = ...,
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.flat_map(
f: collections.abc.Callable[[T, S, V], collections.abc.Awaitable[asyncutils._internal.prots.SupportsIteration[R]]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_: Literal[True],
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.flat_map(
f: collections.abc.Callable[[T, S, V], asyncutils._internal.prots.SupportsIteration[R]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
await_: Literal[False] = ...,
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.flat_map(
f: collections.abc.Callable[[T, S, V, U], collections.abc.Awaitable[asyncutils._internal.prots.SupportsIteration[R]]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_: Literal[True],
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.flat_map(
f: collections.abc.Callable[[T, S, V, U], asyncutils._internal.prots.SupportsIteration[R]],
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[S],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_: Literal[False] = ...,
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.flat_map(
f: collections.abc.Callable[[*tuple[T, ...]], collections.abc.Awaitable[asyncutils._internal.prots.SupportsIteration[R]]],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[True],
strict: bool = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.flat_map(
f: collections.abc.Callable[[*tuple[T, ...]], asyncutils._internal.prots.SupportsIteration[R]],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[False] = ...,
strict: bool = ...,
) types.AsyncGeneratorType[R]

Async version of map that is not a class, with await_ dictating whether the return value of the function is to be awaited before yielding.

async asyncutils.iters.fmap[T, **P](
fs: asyncutils._internal.prots.SupportsIteration[collections.abc.Callable[P, collections.abc.Awaitable[T]]],
/,
*a: P,
**k: P,
) list[T]

Return a list of the results of calling each async function in the first argument (an (async) iterable of functions), with the provided arguments.

asyncutils.iters.fmap_parallel[T, **P](
fs: asyncutils._internal.prots.SupportsIteration[collections.abc.Callable[P, collections.abc.Awaitable[T]]],
/,
*a: P,
**k: P,
) types.AsyncGeneratorType[T]

Like fmap_sequential(), but starts background tasks for each call.

asyncutils.iters.fmap_sequential[T, **P](
fs: asyncutils._internal.prots.SupportsIteration[collections.abc.Callable[P, collections.abc.Awaitable[T]]],
/,
*a: P,
**k: P,
) types.AsyncGeneratorType[T]

Like fmap(), but only call a function after the last completes and the result is gotten.

asyncutils.iters.fuse[T](
it: asyncutils._internal.prots.SupportsIteration[T | None],
end_at: None = ...,
*,
keep_end: bool = ...,
) types.AsyncGeneratorType[T | None]
asyncutils.iters.fuse(
it: asyncutils._internal.prots.SupportsIteration[T | None],
end_at: None = ...,
*,
keep_end: Literal[False] = ...,
yield_after: R,
) types.AsyncGeneratorType[T | R]
asyncutils.iters.fuse(
it: asyncutils._internal.prots.SupportsIteration[T | None],
end_at: None = ...,
*,
keep_end: Literal[True],
yield_after: R,
) types.AsyncGeneratorType[T | R | None]
asyncutils.iters.fuse(
it: asyncutils._internal.prots.SupportsIteration[T | R],
end_at: R,
*,
keep_end: bool = ...,
) types.AsyncGeneratorType[T | R]
asyncutils.iters.fuse(
it: asyncutils._internal.prots.SupportsIteration[T | R],
end_at: R,
*,
keep_end: Literal[False] = ...,
yield_after: V,
) types.AsyncGeneratorType[T | V]
asyncutils.iters.fuse(
it: asyncutils._internal.prots.SupportsIteration[T | R],
end_at: R,
*,
keep_end: Literal[True],
yield_after: V,
) types.AsyncGeneratorType[T | R | V]
asyncutils.iters.gray_product[T](
i1: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R, Ellipsis]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R | V, Ellipsis]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R | V | U, Ellipsis]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R | V | U | S, Ellipsis]]
asyncutils.iters.gray_product(
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
repeat: int = ...,
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]
asyncutils.iters.gray_product(
*its: asyncutils._internal.prots.SupportsIteration[T],
repeat: int = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.group_from[T, R](
keys: asyncutils._internal.prots.SupportsIteration[T],
values: asyncutils._internal.prots.SupportsIteration[R],
strict: bool = ...,
) types.AsyncGeneratorType[tuple[T, types.AsyncGeneratorType[R]]]

Yield tuples of the form (key, group), where group is an async generator taken from values and corresponding to the same run of keys in keys. If strict=False is passed, an error is not raised when keys and values differ in length.

async asyncutils.iters.hamming_dist[T](
a: asyncutils._internal.prots.SupportsIteration[T],
b: asyncutils._internal.prots.SupportsIteration[T],
/,
cmpeq: collections.abc.Callable[[T, T], object] = ...,
) int

Return the Hamming distance between two (async) iterables, using cmpeq to check for equality if passed.

asyncutils.iters.increasing_runs[T: asyncutils._internal.prots.SupportsRichComparison](
it: asyncutils._internal.prots.SupportsIteration[T],
typ: type[T] | None = ...,
max_runs: int = ...,
) types.AsyncGeneratorType[list[T]]
async asyncutils.iters.is_sorted(
it: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsRichComparison],
key: None = ...,
reverse: bool = ...,
strict: bool = ...,
*,
await_key: Literal[False] = ...,
) bool
async asyncutils.iters.is_sorted(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsRichComparison],
reverse: bool = ...,
strict: bool = ...,
*,
await_key: Literal[False] = ...,
) bool
async asyncutils.iters.is_sorted(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
reverse: bool = ...,
strict: bool = ...,
*,
await_key: Literal[True],
) bool
asyncutils.iters.iter_task[T: asyncutils._internal.prots.SupportsIteration[object]](it: T, summaryf: collections.abc.Callable[[T], collections.abc.Awaitable[Any]] = ...) asyncio.Task[float]

Return a task that calls summaryf on the passed (async) iterable and returns the time taken to run it. By default, summaryf consumes it fully.

asyncutils.iters.iterate_with_key[T](
it: asyncutils._internal.prots.SupportsIteration[T],
key: None = ...,
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[T, T]]
asyncutils.iters.iterate_with_key(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], R],
await_key: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[R, T]]
asyncutils.iters.iterate_with_key(
it: asyncutils._internal.prots.SupportsIteration[T],
key: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
await_key: Literal[True],
) types.AsyncGeneratorType[tuple[R, T]]
asyncutils.iters.locate[T](
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], object] = ...,
window_size: None = ...,
*,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[int]
asyncutils.iters.locate(
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
window_size: None = ...,
*,
await_pred: Literal[True],
) types.AsyncGeneratorType[int]
asyncutils.iters.locate(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
window_size: int,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[int]
asyncutils.iters.locate(
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], object],
window_size: int,
*,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[int]
asyncutils.iters.locate(
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[*tuple[T, ...]], collections.abc.Awaitable[object]],
window_size: int,
*,
await_pred: Literal[True],
) types.AsyncGeneratorType[int]
asyncutils.iters.longest_common_prefix[T](*its: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[T]
asyncutils.iters.lstrip[T](
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], object] | None = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.lstrip(
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.map_if_else[T](
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], T],
func_else: None = ...,
*,
await_func: Literal[False] = ...,
await_func_else: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], collections.abc.Awaitable[T]],
func_else: None = ...,
*,
await_func: Literal[True],
await_func_else: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], R],
func_else: collections.abc.Callable[[T], R],
*,
await_func: Literal[False] = ...,
await_func_else: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], R],
func_else: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
*,
await_func: Literal[False] = ...,
await_func_else: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
func_else: collections.abc.Callable[[T], R],
*,
await_func: Literal[True],
await_func_else: Literal[False] = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], object] | None,
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
func_else: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
*,
await_func: Literal[True],
await_func_else: Literal[True],
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], T],
func_else: None = ...,
*,
await_func: Literal[False] = ...,
await_func_else: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], collections.abc.Awaitable[T]],
func_else: None = ...,
*,
await_func: Literal[True],
await_func_else: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], R],
func_else: collections.abc.Callable[[T], R],
*,
await_func: Literal[False] = ...,
await_func_else: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], R],
func_else: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
*,
await_func: Literal[False] = ...,
await_func_else: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
func_else: collections.abc.Callable[[T], R],
*,
await_func: Literal[True],
await_func_else: Literal[False] = ...,
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.map_if_else(
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
it: asyncutils._internal.prots.SupportsIteration[T],
func: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
func_else: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
*,
await_func: Literal[True],
await_func_else: Literal[True],
await_pred: Literal[True],
) types.AsyncGeneratorType[R]
asyncutils.iters.map_on_map[T, R, V](
outer: collections.abc.Callable[[R], V],
inner: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsIteration[R]],
it: asyncutils._internal.prots.SupportsIteration[T],
*,
inner_await: Literal[False] = ...,
outer_await: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[V, Ellipsis]]
asyncutils.iters.map_on_map(
outer: collections.abc.Callable[[R], collections.abc.Awaitable[V]],
inner: collections.abc.Callable[[T], asyncutils._internal.prots.SupportsIteration[R]],
it: asyncutils._internal.prots.SupportsIteration[T],
*,
inner_await: Literal[False] = ...,
outer_await: Literal[True],
) types.AsyncGeneratorType[tuple[V, Ellipsis]]
asyncutils.iters.map_on_map(
outer: collections.abc.Callable[[R], V],
inner: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsIteration[R]]],
it: asyncutils._internal.prots.SupportsIteration[T],
*,
inner_await: Literal[True],
outer_await: Literal[False] = ...,
) types.AsyncGeneratorType[tuple[V, Ellipsis]]
asyncutils.iters.map_on_map(
outer: collections.abc.Callable[[R], collections.abc.Awaitable[V]],
inner: collections.abc.Callable[[T], collections.abc.Awaitable[asyncutils._internal.prots.SupportsIteration[R]]],
it: asyncutils._internal.prots.SupportsIteration[T],
*,
inner_await: Literal[True],
outer_await: Literal[True],
) types.AsyncGeneratorType[tuple[V, Ellipsis]]

Apply a transformation on an (async) iterable on top of another.

asyncutils.iters.map_windows[T, R](
it: asyncutils._internal.prots.SupportsIteration[T],
f: collections.abc.Callable[[*tuple[T, ...]], R],
n: int,
*,
await_: Literal[False] = ...,
star: Literal[True] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.map_windows(
it: asyncutils._internal.prots.SupportsIteration[T],
f: collections.abc.Callable[[*tuple[T, ...]], collections.abc.Awaitable[R]],
n: int,
*,
await_: Literal[True],
star: Literal[True] = ...,
) types.AsyncGeneratorType[R]
asyncutils.iters.map_windows(
it: asyncutils._internal.prots.SupportsIteration[T],
f: collections.abc.Callable[[tuple[T, Ellipsis]], R],
n: int,
*,
await_: Literal[False] = ...,
star: Literal[False],
) types.AsyncGeneratorType[R]
asyncutils.iters.map_windows(
it: asyncutils._internal.prots.SupportsIteration[T],
f: collections.abc.Callable[[tuple[T, Ellipsis]], collections.abc.Awaitable[R]],
n: int,
*,
await_: Literal[True],
star: Literal[False],
) types.AsyncGeneratorType[R]
asyncutils.iters.mark_ends[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[tuple[bool, bool, T]]
asyncutils.iters.mat_vec_mul(
M: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[int]],
V: asyncutils._internal.prots.SupportsIteration[int],
) types.AsyncGeneratorType[int]

Multiplication of a matrix M and a vector V. O(n^2).

asyncutils.iters.merge[T](
*I: asyncutils._internal.prots.SupportsIteration[T],
reverse: bool = ...,
maxqsize: int = ...,
) types.AsyncGeneratorType[T]
Merge items from the (async) iterables into a single async generator, according to the order in which they come.
If reverse is True, the order is reversed, but the returned generator only starts when all items are available.
maxqsize (default MERGE_DEFAULT_MAX_QSIZE) controls the maximum number of items the consumer can fall behind the producers before the producers cease to be advanced.

Caution

If maxqsize is smaller than the total number of items in the sources in reverse mode, a deadlock will occur.

asyncutils.iters.pad_using[T](
it: asyncutils._internal.prots.SupportsIteration[T],
f: collections.abc.Callable[[int], collections.abc.Awaitable[T]],
size: int | None = ...,
*,
await_: Literal[True] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.pad_using(
it: asyncutils._internal.prots.SupportsIteration[T],
f: collections.abc.Callable[[int], T],
size: int | None = ...,
*,
await_: Literal[False],
) types.AsyncGeneratorType[T]
asyncutils.iters.partial_product[T](
i1: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R, Ellipsis]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R, V]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R | V, Ellipsis]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R | V | U, Ellipsis]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
repeat: Literal[1] = ...,
) types.AsyncGeneratorType[tuple[T, R, V, U, S]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[R],
i3: asyncutils._internal.prots.SupportsIteration[V],
i4: asyncutils._internal.prots.SupportsIteration[U],
i5: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
repeat: int,
) types.AsyncGeneratorType[tuple[T | R | V | U | S, Ellipsis]]
asyncutils.iters.partial_product(
i1: asyncutils._internal.prots.SupportsIteration[object],
i2: asyncutils._internal.prots.SupportsIteration[object],
i3: asyncutils._internal.prots.SupportsIteration[object],
i4: asyncutils._internal.prots.SupportsIteration[object],
i5: asyncutils._internal.prots.SupportsIteration[object],
/,
*its: asyncutils._internal.prots.SupportsIteration[object],
repeat: int = ...,
) types.AsyncGeneratorType[tuple[Any, Ellipsis]]
asyncutils.iters.partial_product(
*its: asyncutils._internal.prots.SupportsIteration[T],
repeat: int = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis]]
asyncutils.iters.partitions[T](it: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[list[tuple[T, Ellipsis]]]
async asyncutils.iters.product_index[T](p: tuple[], repeat: int = ...) Literal[0]
async asyncutils.iters.product_index(
p: asyncutils._internal.prots.SupportsIteration[T],
*its: asyncutils._internal.prots.SupportsIteration[T],
repeat: int = ...,
) int
asyncutils.iters.rstrip[T](
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], object] | None = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.rstrip(
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.scan[T, R, V](
f: collections.abc.Callable[[collections.deque[R], T], V],
s: R,
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_: Literal[False] = ...,
) types.AsyncGeneratorType[V]
asyncutils.iters.scan(
f: collections.abc.Callable[[collections.deque[R], T], collections.abc.Awaitable[V]],
s: R,
it: asyncutils._internal.prots.SupportsIteration[T],
/,
*,
await_: Literal[True],
) types.AsyncGeneratorType[V]
asyncutils.iters.scan(
f: collections.abc.Callable[[collections.deque[R], T, U], V],
s: R,
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_: Literal[False] = ...,
) types.AsyncGeneratorType[V]
asyncutils.iters.scan(
f: collections.abc.Callable[[collections.deque[R], T, U], collections.abc.Awaitable[V]],
s: R,
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
await_: Literal[True],
) types.AsyncGeneratorType[V]
asyncutils.iters.scan(
f: collections.abc.Callable[[collections.deque[R], T, U, S], V],
s: R,
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[U],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_: Literal[False] = ...,
) types.AsyncGeneratorType[V]
asyncutils.iters.scan(
f: collections.abc.Callable[[collections.deque[R], T, U, S], collections.abc.Awaitable[V]],
s: R,
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[U],
i3: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
await_: Literal[True],
) types.AsyncGeneratorType[V]
asyncutils.iters.scan(
f: collections.abc.Callable[[collections.deque[R], T, T, T, T, *tuple[T, ...]], V],
s: R,
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[T],
i3: asyncutils._internal.prots.SupportsIteration[T],
i4: asyncutils._internal.prots.SupportsIteration[T],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[False] = ...,
) types.AsyncGeneratorType[V]
asyncutils.iters.scan(
f: collections.abc.Callable[[collections.deque[R], T, T, T, T, *tuple[T, ...]], collections.abc.Awaitable[V]],
s: R,
i1: asyncutils._internal.prots.SupportsIteration[T],
i2: asyncutils._internal.prots.SupportsIteration[T],
i3: asyncutils._internal.prots.SupportsIteration[T],
i4: asyncutils._internal.prots.SupportsIteration[T],
/,
*its: asyncutils._internal.prots.SupportsIteration[T],
await_: Literal[True],
) types.AsyncGeneratorType[V]
async asyncutils.iters.sort_together[T](
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
key_list: asyncutils._internal.prots.SupportsIteration[SupportsIndex] = ...,
key: None = ...,
reverse: bool = ...,
strict: bool = ...,
*,
await_key: Literal[False] = ...,
) list[tuple[T, Ellipsis]]
async asyncutils.iters.sort_together(
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
*,
key: collections.abc.Callable[Ellipsis, asyncutils._internal.prots.SupportsRichComparison],
reverse: bool = ...,
strict: bool = ...,
await_key: Literal[False] = ...,
) list[tuple[T, Ellipsis]]
async asyncutils.iters.sort_together(
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
key_list: asyncutils._internal.prots.SupportsIteration[SupportsIndex],
key: collections.abc.Callable[Ellipsis, asyncutils._internal.prots.SupportsRichComparison],
reverse: bool = ...,
strict: bool = ...,
*,
await_key: Literal[False] = ...,
) list[tuple[T, Ellipsis]]
async asyncutils.iters.sort_together(
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
*,
key: collections.abc.Callable[Ellipsis, collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
reverse: bool = ...,
strict: bool = ...,
await_key: Literal[True],
) list[tuple[T, Ellipsis]]
async asyncutils.iters.sort_together(
its: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.SupportsIteration[T]],
key_list: asyncutils._internal.prots.SupportsIteration[SupportsIndex],
key: collections.abc.Callable[Ellipsis, collections.abc.Awaitable[asyncutils._internal.prots.SupportsRichComparison]],
reverse: bool = ...,
strict: bool = ...,
*,
await_key: Literal[True],
) list[tuple[T, Ellipsis]]
asyncutils.iters.split_when[T](
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T, T], object],
maxsplit: int = ...,
) types.AsyncGeneratorType[list[T]]
asyncutils.iters.stagger[T](
it: asyncutils._internal.prots.SupportsIteration[T],
*,
longest: Literal[False] = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, T, T]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
longest: Literal[False] = ...,
fillvalue: R,
) types.AsyncGeneratorType[tuple[T | R, T, T]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
longest: Literal[True],
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, T | None, T | None]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
*,
longest: Literal[True],
fillvalue: R,
) types.AsyncGeneratorType[tuple[T | R, T | R, T | R]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: tuple[asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: tuple[asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: R,
) types.AsyncGeneratorType[tuple[T | R]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: tuple[asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, T | None]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: tuple[asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: R,
) types.AsyncGeneratorType[tuple[T | R, T | R]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: tuple[asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, T | None, T | None]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: tuple[asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: R,
) types.AsyncGeneratorType[tuple[T | R, T | R, T | R]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: tuple[asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, T | None, T | None, T | None]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: tuple[asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible, asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: R,
) types.AsyncGeneratorType[tuple[T | R, T | R, T | R, T | R]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: None = ...,
) types.AsyncGeneratorType[tuple[T | None, Ellipsis]]
asyncutils.iters.stagger(
it: asyncutils._internal.prots.SupportsIteration[T],
offsets: asyncutils._internal.prots.SupportsIteration[asyncutils._internal.prots.IntCompatible],
*,
longest: bool = ...,
fillvalue: R,
) types.AsyncGeneratorType[tuple[T | R, Ellipsis]]
asyncutils.iters.strip[T](
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], object] | None = ...,
await_pred: Literal[False] = ...,
) types.AsyncGeneratorType[T]
asyncutils.iters.strip(
it: asyncutils._internal.prots.SupportsIteration[T],
pred: collections.abc.Callable[[T], collections.abc.Awaitable[object]],
await_pred: Literal[True],
) types.AsyncGeneratorType[T]
asyncutils.iters.tee[T](it: asyncutils._internal.prots.SupportsIteration[T], n: Literal[1]) tuple[types.AsyncGeneratorType[T]]
asyncutils.iters.tee(
it: asyncutils._internal.prots.SupportsIteration[T],
n: Literal[2] = ...,
*,
maxqsize: int = ...,
put_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]
asyncutils.iters.tee(
it: asyncutils._internal.prots.SupportsIteration[T],
n: Literal[3],
*,
maxqsize: int = ...,
put_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]
asyncutils.iters.tee(
it: asyncutils._internal.prots.SupportsIteration[T],
n: Literal[4],
*,
maxqsize: int = ...,
put_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]
asyncutils.iters.tee(
it: asyncutils._internal.prots.SupportsIteration[T],
n: Literal[5],
*,
maxqsize: int = ...,
put_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]
asyncutils.iters.tee(
it: asyncutils._internal.prots.SupportsIteration[T],
n: Literal[6],
*,
maxqsize: int = ...,
put_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
) tuple[types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T], types.AsyncGeneratorType[T]]
asyncutils.iters.tee(
it: asyncutils._internal.prots.SupportsIteration[T],
n: int,
*,
maxqsize: int = ...,
put_exc: bool = ...,
loop: asyncio.AbstractEventLoop | None = ...,
) tuple[types.AsyncGeneratorType[T], Ellipsis]
Create n independent async generators from a single (async) iterable it that yield the same items, caching items in a queue when needed.
A background task is spawned to consume the iterable.
Unlike itertools.tee(), the returned iterators are plain async generators, and the flattening step with a linked list as specified in the itertools docs is not done.
maxqsize (default TEE_DEFAULT_MAX_QSIZE) specifies how many unproduced items can be consumed from the source ahead of the slowest consumer(s) before the background task and the faster consumers start blocking to wait for them. 0 or below indicates an unbounded queue.
If put_exc is True (default TEE_DEFAULT_PUT_EXC), an exception raised by the source iterable will be propagated as late as possible; that is, only when the caller gets to that point. Slower consumers are not immediately affected.
Otherwise, the exception is raised in the background task used to consume the iterable, and QueueShutDown will be propagated to callers waiting on consumers.
async asyncutils.iters.to_deque[T](it: asyncutils._internal.prots.SupportsIteration[T]) collections.deque[T]

Collect all items in the (async) iterable it into a deque.

async asyncutils.iters.to_list[T](it: asyncutils._internal.prots.SupportsIteration[T]) list[T]

Collect all items of an async iterable into a list. Faster than collect().

async asyncutils.iters.to_set[T: collections.abc.Hashable](it: asyncutils._internal.prots.SupportsIteration[T], frozen: Literal[False] = ...) set[T]
async asyncutils.iters.to_set(it: asyncutils._internal.prots.SupportsIteration[T], frozen: Literal[True]) frozenset[T]

Collect all items in the (async) iterable it into a set or frozenset depending on the frozen parameter (False by default).

async asyncutils.iters.to_tuple[T](it: asyncutils._internal.prots.SupportsIteration[T]) tuple[T, Ellipsis]

Convert the output of to_list() into a tuple.

async asyncutils.iters.vecs_eq[T](
u: asyncutils._internal.prots.SupportsIteration[T],
v: asyncutils._internal.prots.SupportsIteration[T],
cmpeq: collections.abc.Callable[[T, T], object] = ...,
*,
strict: bool = ...,
) bool

Whether the vectors u and v are equal according to cmpeq called on each pair of items from iterating through them in parallel. If strict is False (default True), may return True even for differently-sized vectors.

asyncutils.iters.window[T](
it: asyncutils._internal.prots.SupportsIteration[T],
size: int,
step: int = ...,
) types.AsyncGeneratorType[tuple[T, Ellipsis], tuple[int, int] | None]

Window an async iterable into an async generator of tuples of the specified size and step. You can send in a tuple (size, step) to change the behaviour of the iterator.

asyncutils.locks
Locking primitives, more advanced than or supplementing the functionality of those in asyncio.
All classes strictly follow the asynchronous lock interface as defined by asyncio.Lock and made explicit in the AsyncLockLike protocol,
besides MultiCountDownLatch, since it uses KeyedCondition internally and it is not desired for asyncutils.altlocks to import this submodule as well.
Classes

AdvancedRateLimit

A rate limiter that supports a mode in which waiters can cut the queue.

DynamicBoundedSemaphore

A subclass of asyncio.BoundedSemaphore whose bound can be set by the user via bound.

KeyedCondition

A condition variable that allows waiting on and notifying individual keys, or all keys at once.

MultiCountDownLatch

Wraps a collection of count-down latches, each identified by a key, supporting waiting on individual latches or on all of them at once.

PriorityLock

A lock allowing waiters with a lower priority value to enter first.

PriorityRLock

A re-entrant lock supporting priority.

PrioritySemaphore

A semaphore that allows waiters with a lower priority value to enter first.

RLock

An async re-entrant lock.

Module Contents
class asyncutils.locks.AdvancedRateLimit(rate: float, capacity: float = ..., fair: bool = ...)

Bases: asyncutils._internal.helpers.LoopMixinBase, asyncutils.mixins.LockMixin[None]

A rate limiter that supports a mode in which waiters can cut the queue.

  • rate (required): The initial rate at which tokens refill.

  • capacity: The maximum rate, defaulting to the current rate.

  • fair: Whether to maintain FIFO (first in, first out) for waiters; default True.

async acquire(tokens: float = ..., timeout: float | None = ...) Literal[True]

Acquire the specified number of tokens from the rate limiter (default ADVANCED_RATE_LIMIT_DEFAULT_TOKENS), waiting until the timeout expires and signalling TimeoutError if necessary.

locked() bool

Return True if the limiter is currently locked, such that acquire() must block to wait for tokens.

async release(tokens: float = ...) None

Release the specified number of tokens back to the rate limiter (default ADVANCED_RATE_LIMIT_DEFAULT_TOKENS).

async set_rate(new: float) None

Set the rate of the limiter to new.

update_tokens_lock_held() None

Perform necessary processing before further operations on the token count. It is guaranteed that the rate limiter only calls this when holding the internal lock.

property capacity: float

The capacity of the limiter.

property rate: float

The current rate of the limiter.

property tokens: float

The current number of tokens available.

class asyncutils.locks.DynamicBoundedSemaphore(value: int = ...)

Bases: asyncio.BoundedSemaphore

A subclass of asyncio.BoundedSemaphore whose bound can be set by the user via bound.

value, the initial value of the semaphore, defaults to DYNAMIC_BOUNDED_SEMAPHORE_DEFAULT_VALUE.

property bound: int

The bound of the semaphore. When modified, wake up waiters if the internal value is greater than the new bound.

class asyncutils.locks.KeyedCondition[T](lock: asyncio.Lock | asyncutils.mixins.LockMixin[Any] | None = ...)

Bases: asyncutils.mixins.LockMixin[KeyedCondition[T]], asyncutils.mixins.LoopContextMixin

A condition variable that allows waiting on and notifying individual keys, or all keys at once.

Initialize the condition variable with the given lock, or create a new one if not passed.

async acquire() bool

Wrap the acquire method of the underlying lock to only re-raise critical errors and return success.

assert_locked() None

Ensure that the underlying lock is currently locked, raising a RuntimeError if not.

locked() bool

Return whether the underlying lock is currently locked.

notify(key: T, n: int = ..., strict: bool = ...) None

Notify n waiters waiting on the given key key (default 1). If strict is True and the key doesn’t exist, KeyError is raised.

notify_all(key: T | None = ...) int

Notify all waiters waiting on the given key key, or all waiters if key is None. Return the number of waiters that were notified.

async release() None

Await the release method of the underlying lock if it is a coroutine.

async wait(key: T, timeout: float | None = ...) None

Wait for the given key key to be notified within timeout.

async wait_all(timeout: float | None = ...) None

Wait for all the current waiters to be notified within timeout.

async wait_for(key: T, pred: collections.abc.Callable[[], bool], per_wait_timeout: float | None = ...) None

Keep waiting for the given key key to be notified within per_wait_timeout seconds until the predicate pred returns True.

class asyncutils.locks.MultiCountDownLatch[T: collections.abc.Hashable](counts: collections.abc.Mapping[T, int])

Wraps a collection of count-down latches, each identified by a key, supporting waiting on individual latches or on all of them at once.

Initialize the latch with the given mapping of keys to counts. No more keys can be added after this stage.

async count_down(key: T, strict: bool = ...) None

Decrement the count of the latch with the given key. If it reaches zero, wake up all waiters. If strict is True and the key doesn’t exist, KeyError is raised.

async count_down_all() None

Decrement the count of each latch.

async wait(key: T, strict: bool = ...) None

Wait for the latch with the given key to reach zero. If strict is True and the key doesn’t exist, KeyError is raised.

async wait_all(timeout: float | None = ...) None

Wait until the count of all latches reach zero.

property broken: bool

If this returns True, it means that wait_all() will return immediately.

class asyncutils.locks.PriorityLock

Bases: asyncutils._internal.helpers.LoopMixinBase, asyncutils.mixins.LockWithOwnerMixin[None]

A lock allowing waiters with a lower priority value to enter first.

_release(raise_: bool = ...) None
async acquire(priority: int = ..., timeout: float | None = ...) bool
locked() bool
property is_owner: bool
class asyncutils.locks.PriorityRLock

Bases: RLock

A re-entrant lock supporting priority.

async acquire(priority: int = ..., timeout: float | None = ...) bool
property owner: asyncio.Task[Any] | None
class asyncutils.locks.PrioritySemaphore(value: int = ...)

Bases: asyncutils._internal.helpers.LoopMixinBase, asyncutils.mixins.LockMixin[None]

A semaphore that allows waiters with a lower priority value to enter first.

value, the initial value as an integer, defaults to PRIORITY_SEMAPHORE_DEFAULT_VALUE.

async acquire(priority: int = ...) Literal[True]

Acquire the semaphore with the specified priority, defaulting to 0.

locked() bool

Return True if the semaphore is currently locked.

release(strict: bool = ...) None

Release the semaphore. If strict is True (the default) and the number of releases is more than the number of acquisitions, a RuntimeError is raised.

reset() None

Reset the semaphore to its initial state.

class asyncutils.locks.RLock(lock: asyncutils._internal.prots.AsyncContextManager[Any] | None = ...)

Bases: asyncutils.mixins.LockWithOwnerMixin[None]

An async re-entrant lock.

_release() None
async acquire() Literal[True]
locked() bool
property is_owner: bool
asyncutils.locksmiths

Implementation of a base class for locksmiths, magical entities that can compel not intentionally uncooperative locks to be released while limiting collateral damage and hindrance of the control flow of the program as much as possible and allowing customization of behaviour in different steps regarding some locks.

Classes

ForceResult

The possible results of a force attempt.

LocksmithBase

Instances can attempt to force specific locks asynchronously, and run cleanup or emergency tasks under it as soon as possible; this is especially useful in deadlock scenarios.

RecognitionResult

The possible results of a recognition attempt.

Functions

succeeded(→ TypeIs[Literal[ForceResult.SUCCESS, ...)

Return whether the given result is a successful one.

Module Contents
class asyncutils.locksmiths.ForceResult

Bases: enum.IntEnum

The possible results of a force attempt.

Initialize self. See help(type(self)) for accurate signature.

ALREADY_BEING_FORCED = 4
FAILURE = 5
NO_CURRENT_TASK = 2
OWNER_COMPLETED = 3
RELEASED = 8
RELEASED_WITH_FALSE = 6
SUCCESS = 7
UNFORCEABLE = 1
class asyncutils.locksmiths.LocksmithBase(
loop: asyncio.AbstractEventLoop | None = ...,
lcls: type[asyncutils._internal.prots.AsyncLockLike[Any]] = ...,
)

Instances can attempt to force specific locks asynchronously, and run cleanup or emergency tasks under it as soon as possible; this is especially useful in deadlock scenarios.

Initialize the locksmith. loop is the event loop to use, defaulting to the current running loop. lcls is the type of locks that this locksmith will attempt to force, defaulting to asyncio.Lock.

async _wait_on[T](task: collections.abc.Awaitable[T], lock: asyncutils._internal.prots.AsyncLockLike[Any], /) T

Wait on the task and release the lock. Only called by host() when it successfully acquires the lock; not for public use.

async already_forcing(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) ForceResult

Called when the locksmith attempts to force a lock but it is already being forced by another locksmith, which is detected when the task that owns the lock raises the exception thrown by force() instead of handling it. Its return value is returned by force().

async answer_received(lock: asyncutils._internal.prots.AsyncLockLike[Any], answer: object, /) None

Called when a task that was forced to release the lock responds to the exception thrown by force() by setting a value on it, which is detected by host(). answer is the value that the task set on the exception.

can_force_lock_held(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) bool

Return whether the locksmith can force the lock, given that the internal lock is held. The default implementation allows forcing if the lock is recognized and not currently locked.

async eager_fallback(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) ForceResult

Called when the locksmith attempts to force a lock but the owner task appears to have completed, since it has no coroutine. Its return value is returned by force().

find_owner(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) asyncio.Task[Any] | None

Return the owner of the lock, if it can be found. The default implementation assumes that the _owner attribute of the lock, if present, points to the task that owns it or None.

async force(
lock: asyncutils._internal.prots.AsyncLockLike[Any],
/,
info: object = ...,
*,
purge_waiters: bool = ...,
) ForceResult
The main feature of the locksmith; that is, to try to force the lock lock.
This method cannot be overridden, because it already delegates lock-specific behaviour to overridable methods and handlers in its core logic.
info, if passed, should be an object representing the context of the force attempt, and will be passed to the exception thrown to the
task asking to release the lock.
async get_info(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) Any

Return information about the lock that will be passed to the forcing request.

async host[T](
task: collections.abc.Awaitable[T],
lock: asyncutils._internal.prots.AsyncLockLike[Any],
/,
*,
timeout1: float | None = ...,
timeout2: float | None = ...,
timeout3: float | None = ...,
) T

Run task holding lock immediately after forcing it. The default values of the timeouts are taken from LOCKSMITH_BASE_DEFAULT_TIMEOUTS.

async lock_busy(
lock: asyncutils._internal.prots.AsyncLockLike[Any],
requester: LocksmithBase,
context: dict[str, Any],
/,
) None

Called when a LockForceRequest by a different locksmith propagates, meaning that another locksmith is trying to do the same thing. The context parameter is a dictionary that can be passed to extra of a log record, for example. The implementation is allowed to call lock_busy() on the requester in this method with a modified context, but care should be taken to avoid infinite recursion.

patch_owner(task: asyncio.Task[Any], lock: asyncutils._internal.prots.AsyncLockLike[Any], /) None

Change the owner of the lock to the given task. The default implementation sets the _owner attribute of the lock to the task, if it exists.

preliminary_check_lock(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) bool

Return whether the lock passes preliminary checks for recognition. The default implementation checks whether the lock has the acquire(), release(), and locked() methods.

async purge_waiters(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) None

Clear all waiters on the lock after a force attempt, if necessary. The default implementation assumes this data is attached to the lock as its _waiters attribute, which is a data structure that evaluates to whether it still has any items in a boolean context, with a pop() method.

async recognize_lock(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) RecognitionResult

Recognize the given lock as one that this locksmith can handle.

classmethod register_handler[T: asyncutils._internal.prots.AsyncLockLike[Any]](
h: collections.abc.Callable[[T], object],
/,
*,
shadow: bool = ...,
) collections.abc.Callable[[type[T]], type[T]]

Return a decorator for async lock classes, taking a handler function and returning an identity decorator.

async release_returned_false(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) ForceResult

Called when the locksmith attempts to force a lock and its release method returns False, which is a common convention for indicating that the lock was not actually released. Its return value is returned by force().

async task_propagated_request(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) None

Called when a task that was forced to release the lock does not handle or re-raises the exception.

task_raised_critical(lock: asyncutils._internal.prots.AsyncLockLike[Any], exc: BaseException, /) Literal[ForceResult]

Called when a task raises a critical exception in response to a force request. The default implementation throws the exception wrapped in Critical, rather than returning any value to force(). This is not async because it is imperative that the exception be dealt with quickly. Subclasses can choose to return ForceResult.FAILURE after some handling as well.

async task_raised_other(lock: asyncutils._internal.prots.AsyncLockLike[Any], exc: BaseException, /) None

Called when a task raises a non-critical exception in response to a force request. The default implementation logs the exception if it is not a RuntimeError, since those are commonly raised when a task is cancelled.

async throw_fallback(lock: asyncutils._internal.prots.AsyncLockLike[Any], /) ForceResult

Called when the locksmith attempts to force a lock but there is no current task that owns it or it could not be found, and no task appears to be running. Its return value is returned by force().

wrap_task[T](aw: collections.abc.Awaitable[T], /) asyncio.Task[T]

Wrap the given awaitable in a task using the locksmith’s event loop.

property currently_recognized: frozenset[asyncutils._internal.prots.AsyncLockLike[Any]]

A frozenset of locks that this locksmith currently recognizes.

handlers: ClassVar[dict[type[asyncutils._internal.prots.AsyncLockLike[Any]], collections.abc.Callable[[asyncutils._internal.prots.AsyncLockLike[Any]], Any]]]

A mapping of lock types to handler functions, which are callables that take a lock of the corresponding type and perform any lock-specific logic necessary for forcing it.

class asyncutils.locksmiths.RecognitionResult

Bases: enum.IntEnum

The possible results of a recognition attempt.

Initialize self. See help(type(self)) for accurate signature.

ALREADY_RECOGNIZED = 3
FAILED_ACK = 2
FAILED_PRELIM = 1
SUCCESS = 4
asyncutils.locksmiths.succeeded(
result: object,
/,
) TypeIs[Literal[ForceResult.SUCCESS, ForceResult.RELEASED, RecognitionResult.ALREADY_RECOGNIZED, RecognitionResult.SUCCESS]]

Return whether the given result is a successful one.

asyncutils.misc

Utilities that cannot be easily classified into any submodule.

Classes

CacheWithBackgroundRefresh

CallbackAccumulator

A utility class to store synchronous callbacks and call them sequentially in an executor when the context manager exits.

StateMachine

A simple asynchronous state machine accepting string states.

Functions
Module Contents
class asyncutils.misc.CacheWithBackgroundRefresh[T, R](
ttl: float | None = ...,
refresh: float | None = ...,
*,
default_loader: collections.abc.Callable[[T], R],
processor: collections.abc.Callable[[BaseException, bool], object] = ...,
timer: asyncutils._internal.prots.Timer = ...,
)
class asyncutils.misc.CacheWithBackgroundRefresh(
ttl: float | None = ...,
refresh: float | None = ...,
*,
processor: collections.abc.Callable[[BaseException, bool], object] = ...,
timer: asyncutils._internal.prots.Timer = ...,
)

Bases: asyncutils.mixins.LoopContextMixin

A cache that automatically refreshes entries in the background before expiry. Use as an async context manager only.
Maintains entries with TTL values and proactively reloads their values from registered loaders in the background when they approach expiration.
This ensures availability of fresh data without blocking get operations.

All arguments are optional.

  • ttl: Time-to-live in seconds; default BACKGROUND_REFRESH_CACHE_DEFAULT_TTL.

  • refresh: Time before TTL expires to begin the refresh; default BACKGROUND_REFRESH_CACHE_DEFAULT_REFRESH.

  • processor: Error handler that takes two arguments (exc, was_batched), where exc is the exception occurred and

  • was_batched: Whether the exception was thrown during a batch refresh, in contrast to a single-item refresh.

  • default_loader: The loader to load values from keys for which specific loaders have not been registered.

async __cleanup__() None
__contains__(key: T) bool

Check if a key exists in the cache.

async __setup__() None
async clear() None

Remove all entries from the cache asynchronously.

configure(ttl: float, refresh: float, processor: collections.abc.Callable[[BaseException, bool], object] = ...) None

(Re-)configure the cache with the given ttl, refresh and processor.

expired(key: T) bool

Whether the key has overstayed its TTL.

async get(key: T, loader: collections.abc.Callable[[T], R] | None = ...) R
Get the value for the key from the cache.
If the key is expired, it is immediately loaded; if it is within the refresh window, return the current value and trigger background refresh.
get_loader(key: T) collections.abc.Callable[[T], R]

Get the loader registered for the key, raising LookupError if there is none.

async invalidate(key: T) R | None

Remove a key from the cache, returning the corresponding value if it was in the cache.

async load_item(key: T) None

Load the entry for a key and store it in the cache.

async refresh_item(key: T) None

Refresh an entry in the background.

async refresh_loop() NoReturn

Check for entries requiring refresh and spawning tasks to do so in the background.

register_loader(key: T, loader: collections.abc.Callable[[T], R]) None

Register a specific loader for the key, that will take precedence over the default (if any).

should_refresh(key: T) bool

Whether the key should be refreshed at this instant.

time_past(key: T) ty_extensions.JustFloat

Time having elapsed (in seconds) after the key was last reloaded.

class asyncutils.misc.CallbackAccumulator[T, **P](
name: str,
it: asyncutils._internal.prots.SupportsIteration[collections.abc.Callable[P, T]],
maxlen: int | None = ...,
default: object = ...,
call_once: bool = ...,
default_getter: collections.abc.Callable[[], tuple[collections.abc.Iterable[object], collections.abc.Mapping[str, object]]] = ...,
)
class asyncutils.misc.CallbackAccumulator(
name: str,
*,
maxlen: int | None = ...,
default: object = ...,
call_once: bool = ...,
default_getter: collections.abc.Callable[[], tuple[collections.abc.Iterable[object], collections.abc.Mapping[str, object]]] = ...,
)

Bases: collections.deque[collections.abc.Callable[P, T]], asyncutils.mixins.ExecutorRequiredAsyncContextMixin[CallbackAccumulator[T, P]]

A utility class to store synchronous callbacks and call them sequentially in an executor when the context manager exits.

Tip

To iterate through the callbacks at this moment safely, use the callbacks attribute.

Implementation detail

The fact that this class currently subclasses deque is subject to change.

Initialize the accumulator.

  • name is the name of attribute gotten on the argument to add().

  • maxlen is the maximum number of callbacks that can be stored.

  • default is the default return value of the context manager if no callbacks are added or call_once is False.

  • call_once dictates whether the callbacks will be called only once when the context manager exits, and then cleared.

  • default_getter is a function that returns the default arguments to call the callbacks with when the context manager exits. By default, it returns the exception info if name is '__exit__' and empty arguments otherwise.

__call__(*a: P.args, **k: P.kwargs) None
__enter__() Self

Enter the context manager.

__exit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
__exit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Call the callbacks.

__iter__() types.GeneratorType[collections.abc.Callable[P, T]]

Iterate through the callbacks.

add(o: object, /) None

Get the method on the object with the name specified and queue it to be called.

offer_last(o: object, /) bool

Add a callback from object only if there is space in the accumulator, and return whether it was added.

property callbacks: Self

A view of the callbacks currently stored in the accumulator.

class asyncutils.misc.StateMachine(state: str)

A simple asynchronous state machine accepting string states.

Initialize the state machine with the given initial state.

add(
from_state: str,
to_state: str,
condition: collections.abc.Callable[[str, str], collections.abc.Awaitable[Any]] | None = ...,
) None
Add a condition to the transition from from_state to to_state.
If any condition is None or returns a truthy value taking the current and new states as positional arguments, the transition is allowed.
on_enter[T: collections.abc.Callable[[], collections.abc.Awaitable[Any]]](state: str) collections.abc.Callable[[T], T]

Register an asynchronous handler to be called when state is entered.

on_exit[T: collections.abc.Callable[[], collections.abc.Awaitable[Any]]](state: str) collections.abc.Callable[[T], T]

Register an asynchronous handler to be called when state is exited.

async transition(state: str) bool

Transition from the current state to the new state.

async asyncutils.misc.gather_with_limited_concurrency[T](
n: int = ...,
*coros: collections.abc.Awaitable[T],
ret_exc: Literal[False] = ...,
) list[T]
async asyncutils.misc.gather_with_limited_concurrency(
n: int = ...,
*coros: collections.abc.Awaitable[T],
ret_exc: Literal[True],
) list[T | BaseException]
Gather the given awaitables, but only allow n of them to run at any given moment.
n, which defaults to GATHER_WITH_LIMITED_CONCURRENCY_DEFAULT_MAX_CONCURRENT, is used to restrict the number of concurrently running awaitables.
ret_exc is passed to asyncio.gather() as the return_exceptions argument.
asyncutils.mixins

Mixins classes for some common or specialized patterns that provide methods based on some abstract methods.

Classes

AsyncContextMixin

AwaitableMixin

A subclass that implements wait() automatically becomes awaitable, resolving to the return value of that method.

EventMixin

ExecutorRequiredAsyncContextMixin

Version of AsyncContextMixin that uses an executor to convert the sync context manager methods to async in an event loop.

LockMixin

A mixin to derive __aenter__() and __aexit__() from acquire() and release() of subclasses.

LockWithOwnerMixin

Mixin for locks that can report their owner (the task currently holding it).

LoopContextMixin

Like TaskGroup, but manages an event loop publicly, allows custom setup and teardown logic and waits for the cancellations to complete on exit.

Module Contents
class asyncutils.mixins.AsyncContextMixin[T]

Bases: abc.ABC

A mixin to derive __aenter__() and __aexit__() from __enter__() and __exit__() of subclasses.
__enter__() is optional and returns self by default, but that cannot be typed accurately.
async __aenter__() T
async __aexit__(
exc_typ: asyncutils._internal.prots.ExcType,
exc_val: BaseException,
exc_tb: types.TracebackType,
/,
) bool | None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) Literal[False] | None
__enter__() T
abstractmethod __exit__(
exc_typ: asyncutils._internal.prots.ExcType,
exc_val: BaseException,
exc_tb: types.TracebackType,
/,
) bool | None
abstractmethod __exit__(exc_typ: None, exc_val: None, exc_tb: None, /) Literal[False] | None
class asyncutils.mixins.AwaitableMixin[T]

Bases: abc.ABC

A subclass that implements wait() automatically becomes awaitable, resolving to the return value of that method.

__await__() types.GeneratorType[Any, None, T]

Await statement support.

abstractmethod wait() collections.abc.Awaitable[T]
class asyncutils.mixins.EventMixin[T]

Bases: AwaitableMixin[T], asyncutils._internal.helpers.LoopMixinBase, abc.ABC

Mixin for event classes that don’t inherit from asyncio.Event but provide enhanced functionality with the same API and some mixin methods, most notably making the event itself awaitable.
This is simply syntactic sugar for calling the wait method, but more convenient and intuitive when thinking of events as reusable futures.
abstractmethod clear() None

Clear the value of the event.

abstractmethod get() T

Return the value currently held by the event, or raise an exception if there is no value set. The implementations in this library have a dedicated exception type, EventValueError, for this.

abstractmethod is_set() bool

Return whether the event currently holds a value.

abstractmethod set(value: T) None

Set the value of the event and wake up all waiters. Implementations may not choose to clear the value within this method.

async wait(timeout: float | None = ...) T

Wait for the event with an optional timeout and return its value.

abstractmethod wait_for_next(timeout: float | None = ...) T
Async:

Wait for the next time the event is set, and return the value it was set to. Should always block even if there is currently a value set.

async wait_for_value(val: T, timeout: float | None = ..., *, set_at_timeout: bool = ...) None

Wait for the event to be set to a specific value val, with an optional timeout. If set_at_timeout is True, the event will be set to val when the timeout occurs, and waiters will be woken up. The value will persist on the event by default in this case.

class asyncutils.mixins.ExecutorRequiredAsyncContextMixin[T]

Bases: abc.ABC

Version of AsyncContextMixin that uses an executor to convert the sync context manager methods to async in an event loop.

async __aenter__() T
async __aexit__(
exc_typ: asyncutils._internal.prots.ExcType,
exc_val: BaseException,
exc_tb: types.TracebackType,
/,
) bool | None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) Literal[False] | None
__enter__() T
abstractmethod __exit__(
exc_typ: asyncutils._internal.prots.ExcType,
exc_val: BaseException,
exc_tb: types.TracebackType,
/,
) bool | None
abstractmethod __exit__(exc_typ: None, exc_val: None, exc_tb: None, /) Literal[False] | None
property runner: collections.abc.Callable[[collections.abc.Callable[[*Ts], R], *Ts], asyncio.Future[R]]
class asyncutils.mixins.LockMixin[T]

Bases: abc.ABC

A mixin to derive __aenter__() and __aexit__() from acquire() and release() of subclasses.

async __aenter__() T

Acquire the lock and return an object of the implementation’s choice.

async __aexit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Release the lock and optionally perform handling according to the exception occurred.

classmethod __init_subclass__(*, _lock_factory_: collections.abc.Callable[[Self], T] = ..., **k: object) None
acknowledge_locksmith_lock_held(
smith: asyncutils.locksmiths.LocksmithBase,
/,
) bool | collections.abc.Coroutine[Any, Any, bool]

Cooperate with locksmiths in case of unusually long wait times for the lock which may indicate deadlock, livelock or starvation. Optional.

abstractmethod acquire() bool
Async:

Acquire the lock, waiting if necessary. Return whether the lock was acquired successfully. Some locks may raise an error if not; that is up to the implementation.

abstractmethod locked() bool

Return whether the lock is currently held by a task satisfying a certain criterion (e.g. it is exactly the task that awaited the acquire() call).

abstractmethod release() collections.abc.Coroutine[Any, Any, None] | None

Release the lock. Some locks may require this to be called from a task that holds the lock, or may raise an error if the lock is not currently held; that is up to the implementation.

class asyncutils.mixins.LockWithOwnerMixin[R: (None, collections.abc.Coroutine[Any, Any, None])]

Bases: LockMixin[None]

Mixin for locks that can report their owner (the task currently holding it).

abstractmethod _release() R

Will be wrapped by release() to throw RuntimeError if the current task is not the owner of the lock.

release() R

Release the lock. Some locks may require this to be called from a task that holds the lock, or may raise an error if the lock is not currently held; that is up to the implementation.

property is_owner: bool
Abstractmethod:

Should evaluate to True if the current task is the owner of the lock.

class asyncutils.mixins.LoopContextMixin

Bases: asyncutils._internal.helpers.LoopMixinBase

Like TaskGroup, but manages an event loop publicly, allows custom setup and teardown logic and waits for the cancellations to complete on exit.

async __aenter__() Self

Call __setup__() and return self.

async __aexit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Call __cleanup__() and cancel all running tasks in the loop.

async __cleanup__() None

Default implementation does nothing.

async __setup__() None

Default implementation does nothing.

property loop: asyncio.AbstractEventLoop

The underlying event loop.

property running_tasks: set[asyncio.Task[Any]]

A set of all tasks currently running in the underlying loop.

asyncutils.networking

Some asyncio protocols and a transport. See the asyncio documentation page.

Classes

CRLFProtocol

Carriage Return + Line Feed (CRLF) protocol for Windows.

CRProtocol

Carriage Return (CR) protocol. For legacy systems no longer officially supported by Python, such as Mac OS 9, such that this will never be chosen as the default.

LFProtocol

Line Feed (LF) protocol for Unix-like systems.

LineProtocol

SocketTransport

A thread-unsafe transport designed to connect LineProtocol's to sockets. Subclasses may choose to support more protocols.

Module Contents
class asyncutils.networking.CRLFProtocol

Bases: LineProtocol

Carriage Return + Line Feed (CRLF) protocol for Windows.

class asyncutils.networking.CRProtocol

Bases: LineProtocol

Carriage Return (CR) protocol. For legacy systems no longer officially supported by Python, such as Mac OS 9, such that this will never be chosen as the default.

class asyncutils.networking.LFProtocol

Bases: LineProtocol

Line Feed (LF) protocol for Unix-like systems.

class asyncutils.networking.LineProtocol

Bases: asyncio.Protocol, asyncutils._internal.helpers.LoopMixinBase

An implementation of Protocol providing line-based buffering and writing. Not thread-safe.
The idea was originally introduced in PEP 3153, but did not see eventual adaptation in the standard library.
This particular implementation is designed to be used with SocketTransport, though other transports can enforce it too.
Instantiating this class will give an LFProtocol or CRLFProtocol depending on os.linesep.
close() bool

Close the transport and return success.

connection_lost(exc: Exception | None) None

Called when the connection is lost.

connection_made(transport: asyncio.WriteTransport) None

Unlike the base class, this method does not take read-only transports.

data_received(data: bytes, bufsize: int = ...) None

Called when some data is received, with data being a non-empty bytes object containing it.

async drain() None

Wait until the transport is ready for more data to be written (i.e. the write buffer is flushed).

eof_received() None

Receive the signal from the other end that it won’t send any more data, for example when write_eof() is called, which closes the transport.

flush() None

Flush the internal buffer and put in remaining data as a single line.

pause_writing() None

Called when the transport’s buffer goes over the high watermark.

async read_line() str | None

Read a line from the internal buffer and return it, or None if EOF is reached.

resume_writing() None

Called when the transport’s buffer drains below the low watermark.

signal_eof() None

Signal that the stream is at EOF.

write_line(line: str) None

Write the string line to the transport, followed by the newline sequence.

async write_line_with_backpressure(line: str) None

Write the string line to the transport, followed by the newline sequence, after draining it.

write_literal(data: bytes) None

Write the given bytes into the transport without appending a newline.

async write_literal_with_backpressure(data: bytes) None

Write the given bytes into the transport without appending a newline, after draining it.

CARRIAGE_RETURN: ClassVar[bytes]

The carriage return sequence used by this protocol as bytes.

NEWLINE: ClassVar[bytes]

The newline sequence used by this protocol as bytes.

property connected_transport: asyncio.WriteTransport

The transport associated with this protocol; raises ConnectionError if not connected.

property transport: asyncio.WriteTransport | None

The transport associated with this protocol, or None if not connected.

class asyncutils.networking.SocketTransport(sock: socket.socket | None = ...)

Bases: asyncio.Transport

A thread-unsafe transport designed to connect LineProtocol’s to sockets. Subclasses may choose to support more protocols.

Initialize the transport, connecting the socket immediately if given.

abort() None

Close the transport immediately, without waiting for pending operations to complete.

can_write_eof() Literal[True]

Stub implementation that always returns True.

close(e: Exception | None = ...) None

Close the transport and flush the outgoing data buffer. No more data will be received. After all buffered data is flushed, the protocol’s connection_lost() method will be called with None as argument. The transport is not to be used once closed.

connect_sock(sock: socket.socket = ...) None

Connect the transport to the given socket.

disconnect_sock() socket.socket | None

Disconnect the transport from its socket and return it, or None if not connected.

get_protocol() LineProtocol

Return the current protocol. For this class, it is expected to always be a LineProtocol or one of its subclasses.

get_write_buffer_limits() tuple[int, int]

Get the high and low watermarks for write flow control. Return a tuple (low, high), where low and high are positive number of bytes.

get_write_buffer_size() int

Return the current size of the output buffer used by the transport.

is_closing() bool

Return whether the transport is closing or already closed.

set_write_buffer_limits(high: int | None = ..., low: int | None = ...) None

Set the high and low watermarks for write flow control in bytes.

sock_context(sock: socket.socket) asyncutils._internal.prots.DualContextManager[None]

Return a context manager, that works in both sync and async, that connects the transport to the given socket on entry and disconnects it on exit.

write(data: collections.abc.Iterable[int]) None

Write the given iterable over integers in range(256) interpreted as characters into the transport.

write_eof() None

Close the write end of the transport after flushing all buffered data. Data may still be received.

property loop: asyncio.AbstractEventLoop

Override this if the type of the protocols this transport accepts is altered in subclasses.

ptc: type[asyncio.Protocol]

The protocol class this transport should use.

asyncutils.pools

Various pool implementations for concurrent execution and resource management in asynchronous contexts.

Classes

AdvancedPool

A pool implementation used to call sync functions concurrently in an async-first interface, managing event loop and threading resource shenanigans internally.

ConnectionPool

A pool managing resources in a simple and intuitive lock interface, with support for health checking, auto-recycling and dynamic rescaling.

Module Contents
class asyncutils.pools.AdvancedPool(
max_workers: int = ...,
min_workers: int = ...,
qsize: int = ...,
scaling: bool = ...,
kill_at_exit: bool = ...,
)

Bases: asyncutils.mixins.LoopContextMixin

A pool implementation used to call sync functions concurrently in an async-first interface, managing event loop and threading resource shenanigans internally.

Caution

Use instances of this class as async context managers only.

All arguments are optional.

  • max_workers controls the maximum number of workers (threads) that can run concurrently. Defaults to ADVANCED_POOL_DEFAULT_MAX_WORKERS.

  • min_workers determines the least number of threads there will be at any instance. Defaults to ADVANCED_POOL_DEFAULT_MIN_WORKERS.

  • qsize sets the maximum number of pending tasks that can be queued. If not passed, there is no limit.

  • scaling enables dynamic scaling of the pool based on workload. The default is True.

  • kill_at_exit determines whether the shut down when the context manager exits should be immediate. Default False.

async __cleanup__() None
__del__() None

Shut down the pool synchronously with a short timeout if needed. To avoid this blocking up GC, shut down the pool explicitly by using it as an async context manager.

async complete[T, **P](f: collections.abc.Callable[P, T], *a: P, **k: P) T
async complete(f: collections.abc.Callable[Ellipsis, T], *a: object, _priority_: int, **k: object) T

Wait for a sync function to complete its execution by the pool asynchronously and get its result.

async double_starmap[T](
f: collections.abc.Callable[Ellipsis, T],
/,
it: asyncutils._internal.prots.SupportsIteration[collections.abc.Mapping[str, Any]],
priority: int = ...,
) list[T]

Like map(), but the iterable should yield dicts that are unpacked as keyword arguments to the function.

async drain() None

Wait until all pending tasks have been completed.

async join() list[int | BaseException]

Return a list containing the number of tasks completed by each worker in a random order or an exception if a worker thread has been terminated by an unhandled exception.

async map[R, T](
f: collections.abc.Callable[[R], T],
it: asyncutils._internal.prots.SupportsIteration[R],
/,
*,
priority: int = ...,
strict: bool = ...,
) list[T]
async map(
f: collections.abc.Callable[[R, V], T],
i1: asyncutils._internal.prots.SupportsIteration[R],
i2: asyncutils._internal.prots.SupportsIteration[V],
/,
*,
priority: int = ...,
strict: bool = ...,
) list[T]
async map(
f: collections.abc.Callable[[R, V, U], T],
i1: asyncutils._internal.prots.SupportsIteration[R],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[U],
/,
*,
priority: int = ...,
strict: bool = ...,
) list[T]
async map(
f: collections.abc.Callable[[R, V, U, S], T],
i1: asyncutils._internal.prots.SupportsIteration[R],
i2: asyncutils._internal.prots.SupportsIteration[V],
i3: asyncutils._internal.prots.SupportsIteration[U],
i4: asyncutils._internal.prots.SupportsIteration[S],
/,
*,
priority: int = ...,
strict: bool = ...,
) list[T]
async map(
f: collections.abc.Callable[Ellipsis, T],
/,
*its: asyncutils._internal.prots.SupportsIteration[Any],
priority: int = ...,
strict: bool = ...,
) list[T]

Apply the function f to the items from the iterables in a concurrent manner, returning the results in a list. If strict is True, all iterables must have the same length.

raise_for_shutdown() None

Raise PoolShutDown if the pool is shutting down or has been shut down.

async resize(min_workers: int, max_workers: int) None

Adjust the lower and upper limits of the pool size, and destroy or spawn threads accordingly.

async shutdown(
cancel_pending: bool = ...,
idle_timeout: float | None = ...,
total_timeout: float | None = ...,
) ty_extensions.JustFloat

Shut down the pool, waiting for all workers to finish their current tasks, and return the total time the pool has been active. If cancel_pending is True, pending tasks that have not been picked up by workers will be cancelled immediately. If idle_timeout is passed, it will limit the time used to join the task queue.

async starmap[T, *Ts](
f: collections.abc.Callable[[*Ts], T],
/,
it: asyncutils._internal.prots.SupportsIteration[tuple[*Ts]],
priority: int = ...,
) list[T]

Like map(), but the iterables should yield tuples that are unpacked as arguments to the function.

async starmap_with_kwds[T](
f: collections.abc.Callable[Ellipsis, T],
/,
it: asyncutils._internal.prots.SupportsIteration[tuple[asyncutils._internal.prots.SupportsIteration[Any], collections.abc.Mapping[str, Any]]],
priority: int = ...,
) list[T]

Like map(), but the iterable should yield tuples of the form (args, kwargs), where args is an iterable of positional arguments and kwargs is a mapping of keyword arguments.

async submit[T, **P](f: collections.abc.Callable[P, T], *a: P, **k: P) asyncio.Future[T]
async submit(f: collections.abc.Callable[Ellipsis, T], *a: object, _priority_: int, **k: object) asyncio.Future[T]

Schedule a sync function to be executed in a worker thread, waiting asynchronously until there is enough space in the internal queue from which workers fetch tasks if necessary, and get an async future to access its result.

submit_nowait[T, **P](f: collections.abc.Callable[P, T], *a: P, **k: P) asyncio.Future[T]
submit_nowait(f: collections.abc.Callable[Ellipsis, T], *a: object, _priority_: int, **k: object) asyncio.Future[T]

Schedule a sync function to be executed in a worker thread, raising asyncio.QueueFull if there is not enough space in the internal queue from which workers fetch tasks, and get an async future to access its result.

async wait_for_slot(timeout: float | None = ...) ty_extensions.JustFloat

Wait until there is a slot in the internal queue for pending tasks, and return the time spent waiting. If timeout is passed, it will limit the waiting time.

property completed: int

The total number of tasks completed by the pool.

property empty: bool

Whether the internal queue for pending tasks is empty.

property full: bool

Whether the internal queue for pending tasks is full, such that wait_for_slot() will block.

property idle: bool

Whether all workers are idle, i.e. not executing any tasks currently. This also implies empty is True.

property qsize: int

The current number of pending tasks in the internal queue.

property uptime: ty_extensions.JustFloat

The time in seconds since the pool started.

class asyncutils.pools.ConnectionPool[T, **P](
factory: collections.abc.Callable[P, T],
maxsize: int = ...,
minsize: int = ...,
maxlife: float = ...,
healthchecker: collections.abc.Callable[[T], bool] | None = ...,
cleaner: collections.abc.Callable[[T], None] | None = ...,
)

Bases: asyncutils._internal.helpers.LoopMixinBase

A pool managing resources in a simple and intuitive lock interface, with support for health checking, auto-recycling and dynamic rescaling.

Caution

Use instances of this class as async context managers only.

All arguments except factory, which should be a callable returning a connection, are optional.

  • maxsize controls the maximum number of connections that can be created. Defaults to CONNECTION_POOL_DEFAULT_MAX_SIZE.

  • minsize determines the least number of connections that will be maintained at any instance. Defaults to CONNECTION_POOL_DEFAULT_MIN_SIZE.

  • maxlife sets the maximum lifetime of a connection in seconds, after which it will be recycled. Defaults to CONNECTION_POOL_DEFAULT_MAX_LIFE.

  • healthchecker is a function that takes a connection and returns whether it is healthy. If not passed, connections are assumed to always be healthy.

  • cleaner is a function that takes a connection and performs necessary cleanup before it is recycled. If not passed, no cleanup will be performed.

async __aenter__() Self

Start and return the pool.

async __aexit__(exc_typ: asyncutils._internal.prots.ExcType, exc_val: BaseException, exc_tb: types.TracebackType, /) None
async __aexit__(exc_typ: None, exc_val: None, exc_tb: None, /) None

Stop the pool, closing all connections.

async acquire(*a: P.args, **k: P.kwargs) T

Acquire a connection from the pool, waiting asynchronously until one is available if necessary. The arguments will be passed to the connection factory when creating new connections if needed.

async create_connection(*a: P.args, **k: P.kwargs) T
async create_connection(*a: object, _executor_: asyncutils.config.Executor | None, **k: object) T

Call the connection factory with the given parameters and return a new connection object.

async release(conn: T, /, *a: P.args, **k: P.kwargs) None

Release a connection back to the pool after use. The arguments will be passed to the connection factory when creating new connections if needed, and can be used by the cleaner for cleanup if necessary.

async start(
akgen: asyncutils._internal.prots.SupportsIteration[tuple[collections.abc.Iterable[Any], collections.abc.Mapping[str, Any]]] | None = ...,
executor: asyncutils.config.Executor | None = ...,
) None

Spawn the connections using the arguments from the parameter generator. The factory is run in the executor passed to make it async.

async stop() None

Close all connections and stop the pool.

property available: int

The number of connections currently available for acquisition.

property cursize: int

The current number of connections managed by the pool, including those in use and those available.

property in_use: int

The number of connections currently in use.

property maxlife: float

The maximum lifetime of a connection in seconds.

property maxsize: int

The maximum number of connections that can be created by the pool.

property minsize: int

The minimum number of connections that will be maintained by the pool.

asyncutils.processors

Processors for asynchronous tasks.

Classes

BatchProcessor

Call a processor with items batched to a certain size from different sources, with an optional time limit for batches.

BoundedBatchProcessor

Call a processor with items batched to a certain size from different sources with bounded concurrency.

Bulkhead

Limit the number of concurrent executions of coroutines, with an optional queue for pending executions and an optional callback that handles exceptions raised by the processor.

Module Contents
class asyncutils.processors.BatchProcessor[T](
processor: collections.abc.Callable[[list[T]], collections.abc.Awaitable[None]],
*,
maxsize: int = ...,
maxtime: float = ...,
timer: asyncutils._internal.prots.Timer = ...,
)

Bases: asyncutils.mixins.LoopContextMixin

Call a processor with items batched to a certain size from different sources, with an optional time limit for batches.

Caution

Use instances of this class as async context managers to ensure proper cleanup.

maxsize defaults to BATCH_PROCESSOR_DEFAULT_MAX_SIZE, maxtime to BATCH_PROCESSOR_DEFAULT_MAX_TIME, and timer time.monotonic().

async __cleanup__() None
async __setup__() None
async add(item: T) None

Add an item to the current batch. If the batch is full, process it asynchronously before returning.

async flush() None

Process the items in the buffer, even if the batch size is not reached.

property time_since_last_process: ty_extensions.JustFloat

The time in seconds since the last batch was processed.

class asyncutils.processors.BoundedBatchProcessor[T, R](
processor: collections.abc.Callable[[list[T]], collections.abc.Awaitable[R]],
batch: int = ...,
max_concurrent: int = ...,
)

Call a processor with items batched to a certain size from different sources with bounded concurrency.

batch defaults to BOUNDED_BATCH_PROCESSOR_DEFAULT_BATCH_SIZE and max_concurrent BOUNDED_BATCH_PROCESSOR_DEFAULT_MAX_CONCURRENT.

process(items: asyncutils._internal.prots.SupportsIteration[T]) types.AsyncGeneratorType[R]

Call the processor on batches of items from the source and yield the results as they arrive.

class asyncutils.processors.Bulkhead(
max_concurrent: int,
*,
max_queue: int = ...,
max_rej: int = ...,
exc: asyncutils._internal.prots.CanExcept = ...,
processor: collections.abc.Callable[[BaseException], collections.abc.Awaitable[None]] = ...,
)

Bases: asyncutils.mixins.LoopContextMixin

Limit the number of concurrent executions of coroutines, with an optional queue for pending executions and an optional callback that handles exceptions raised by the processor.

Caution

Use instances of this class as async context managers to ensure proper cleanup.

  • max_concurrent (required): maximum number of concurrent executions allowed

  • max_queue: maximum number of pending executions allowed in the queue; if the queue is full, new executions will be rejected until there is space in the queue. Non-positive value means no limit (there is currently no way to get a zero-capacity queue). Default BULKHEAD_DEFAULT_MAX_QUEUE.

  • max_rej: maximum number of rejections allowed before the bulkhead shuts down and rejects all new executions. Negative value means no limit. Default BULKHEAD_DEFAULT_MAX_REJ.

  • exc: the type of exceptions that the processor may raise and should be caught and passed to the processor callback. Default Exception.

async __cleanup__() None
async execute(coro: collections.abc.Awaitable[Any]) None

Queue a coroutine coro to be executed and execute a coroutine that may not be the same as coro. Bulkhead constraints are applied, and the return value is lost.

async shutdown(timeout: float | None = ...) list[collections.abc.Awaitable[Any]]

Shut down the bulkhead and return all incomplete tasks.

async wait_for_shutdown(timeout: float | None = ...) None

Wait until the bulkhead enters the shutdown phase.

async wait_until_idle(timeout: float | None = ...) Literal[True]

Wait until no tasks are running.

property active_tasks: int

The number of currently running tasks.

property available_queue_slots: float

The number of available slots in the task queue. Gives an integer, unless the queue is unbounded, in which case math.inf is returned.

property available_slots: int

The number of slots available on the bulkhead.

property curr_qsize: int

The current size of the task queue.

property is_shutdown: bool

Whether the bulkhead is shutting down or has been shut down, possibly because too many executions were rejected.

property max_qsize: int

The maximum size of the task queue.

property rejected: int

The number of rejected executions so far.

asyncutils.properties

Asynchronous descriptors, mimicking property and optionally applying a lock.

Classes

AsyncPropertyBase

A property with asynchronous getters, setters and deleters.

ConcurrentAsyncProperty

Allows set and delete operations to run concurrently once the operations are called, without any guarantee on the order of execution.

Deleters

Integer flags configuring a fallback deleter for async properties.

LazyAsyncProperty

A property that queues set and delete operations.

RWLockedAsyncProperty

Apply a reader-writer lock to the property. Naturally, setters and deleters are writers and getters are readers.

Module Contents
class asyncutils.properties.AsyncPropertyBase[T, R]

Bases: abc.ABC

A property with asynchronous getters, setters and deleters.

Create a new async property with getter fget, setter fset and deleter fdel.
fget must return an awaitable resolving to the value of the property and take only the instance as argument.
fset should take the instance and value as arguments.
fdel can be a callable taking the instance as an argument, or a member of Deleters to configure a basic deleter that disallows gets after deletion on the instance in question.
If the getter is not provided, return a partial decorator instead. In that overload, none of the accessors are to be passed.
doc, if passed, will be the docstring of the property in the form of the __doc__ attribute. Otherwise, an attempt is made to find it on the getter.
strict, which defaults to True, controls whether performing an operation that invokes an unset accessor is allowed.
If mutable is True (default False), the property can be reassigned and deleted on the class.
If assert_modifiers_return_none=False is not passed, the setter and deleter must both return None or an awaitable resolving to None, which will be awaited.
If hide is True (default False), accessing the attribute on the class it is defined in would raise AttributeError as if the property didn’t exist.
Subclasses must define wrap_aw(), and are allowed to override _init() and _repr_accessor(). Nothing else is customizable.
__delete__(instance: R, /) None

Note that the deleter is to be called with the instance as the only argument.

__get__(instance: R, owner: type[R] | None = ..., /) types.CoroutineType[Any, Any, T]
__get__(instance: None, owner: type[R], /) types.CoroutineType[Any, Any, Self]

Call the getter and return a coroutine resolving to its result.

__getattr__(name: str, /) Any

Find the attribute on the getter if it exists.

classmethod __init_subclass__(
/,
*,
lock_factory: collections.abc.Callable[[],
asyncutils._internal.prots.AsyncContextManager[Any]]=...,
**k: object,
) None

lock_factory, a callable that returns a new per-instance async context manager, is required for immediate subclasses.

__reduce__() str

Return the qualified name of this property for pickling. Hidden properties cannot be pickled.

__set__(instance: R, value: T, /) None

Note that the setter is to be called with the instance and value as arguments.

__set_name__(owner: type[R], name: str, /) None

Bind the property to the class.

_init(
fget: collections.abc.Callable[[R], collections.abc.Awaitable[T]],
/,
fset: collections.abc.Callable[[R, T], collections.abc.Awaitable[None] | None] | None = ...,
fdel: collections.abc.Callable[[R], collections.abc.Awaitable[None] | None] | Deleters = ...,
*,
doc: str | None = ...,
strict: bool = ...,
hide: bool = ...,
mutable: bool = ...,
assert_modifiers_return_none: bool = ...,
) None

Set the necessary attributes on the property; called at construction.

static _repr_accessor(
accessor: collections.abc.Callable[Concatenate[R, Ellipsis], collections.abc.Awaitable[T | None] | None] | Deleters | None,
/,
) str

Return a string representing an accessor. Called by the implementation of __repr__().

deleter(fdel: collections.abc.Callable[[R], collections.abc.Awaitable[None] | None] | Deleters, /) Self

Return another async property with the given function as the deleter.

getter(fget: collections.abc.Callable[[R], collections.abc.Awaitable[T]], /) Self

Return another async property with the given function as the getter.

setter(fset: collections.abc.Callable[[R, T], collections.abc.Awaitable[None] | None], /) Self

Return another async property with the given function as the setter.

abstractmethod wrap_aw[S](aw: collections.abc.Awaitable[S], /) collections.abc.Awaitable[S]

Return an awaitable resolving to the result of an awaitable, limited to those returned by the setter or deleter. This can be a coroutine, a future, a task or anything else, and affects the strategy used to handle assignments and deletions which must return synchronously but run in the background.

__doc__: str | None

The docstring for this property, or None if it doesn’t exist.

__module__: str | None

The module this property is defined in, determined by the function it decorates.

__name__: str

The name of this property, determined by the function it decorates.

property fdel: collections.abc.Callable[[R], collections.abc.Awaitable[None] | None] | Deleters

The deleter for this property.

property fget: collections.abc.Callable[[R], collections.abc.Awaitable[T]] | None

The getter function for this property, or None if it doesn’t exist.

property fset: collections.abc.Callable[[R, T], collections.abc.Awaitable[None] | None] | None

The setter function for this property, or None if it doesn’t exist.

class asyncutils.properties.ConcurrentAsyncProperty[T, R]

Bases: AsyncPropertyBase[T, R]

Allows set and delete operations to run concurrently once the operations are called, without any guarantee on the order of execution.

The setters and deleters can be implemented acquire a writer lock and the getter the corresponding reader lock from rwlocks with its lock policies that provide fluent decorator interfaces.
Note, however, that the accessor decorators must be outermost because they turn callables into properties.
wrap_aw[S](aw: collections.abc.Awaitable[S], /) asyncio.Task[S]

Return a task for the awaitable returned by the setter or deleter.

__doc__: str | None

The docstring for this property, or None if it doesn’t exist.

__module__: str | None

The module this property is defined in, determined by the function it decorates.

__name__: str

The name of this property, determined by the function it decorates.

class asyncutils.properties.Deleters

Bases: enum.IntFlag

Integer flags configuring a fallback deleter for async properties.

Initialize self. See help(type(self)) for accurate signature.

CANNOT_SET_AFTER_DELETE = 1

This flag is only meaningful if NO_DELETER is not set. Setting this flag means the setter will not be allowed to run after the deleter has been executed on an instance.

CAN_DELETE_AGAIN = 2

If this flag is set, the deleter can be called multiple times on the same instance without raising AttributeError.

DEFAULT = 0

The default deleter.

NO_DELETER = 4

If this flag is set, the attribute still exists on the object after deletion, just like there was no deleter, if SILENT is set.

SILENT = 1

This flag is only meaningful if NO_DELETER is also set. Deletion will essentially become a no-op in that case, as opposed to the default behaviour which raises AttributeError.

class asyncutils.properties.LazyAsyncProperty[T, R]

Bases: AsyncPropertyBase[T, R]

A property that queues set and delete operations.

Operations are completed only when a get is called, strictly in order.

async wrap_aw[S](aw: collections.abc.Awaitable[S], /) S

Wrap the awaitable in a coroutine, run lazily.

__doc__: str | None

The docstring for this property, or None if it doesn’t exist.

__module__: str | None

The module this property is defined in, determined by the function it decorates.

__name__: str

The name of this property, determined by the function it decorates.

class asyncutils.properties.RWLockedAsyncProperty[T, R]

Bases: ConcurrentAsyncProperty[T, R]

Apply a reader-writer lock to the property. Naturally, setters and deleters are writers and getters are readers.

policy is the class used to create the readers-writer lock for the property. It must subclass RWLock.

_init(
f: collections.abc.Callable[[R], collections.abc.Awaitable[T]],
/,
fset: collections.abc.Callable[[R, T], collections.abc.Awaitable[None] | None] | None = ...,
fdel: collections.abc.Callable[[R], collections.abc.Awaitable[None] | None] | Deleters = ...,
*,
policy: type[asyncutils.rwlocks.RWLock] = ...,
doc: str | None = ...,
strict: bool = ...,
hide: bool = ...,
mutable: bool = ...,
assert_modifiers_return_none: bool = ...,
) None

Set the necessary attributes on the property; called at construction.

__doc__: str | None

The docstring for this property, or None if it doesn’t exist.

__module__: str | None

The module this property is defined in, determined by the function it decorates.

__name__: str

The name of this property, determined by the function it decorates.

asyncutils.queues

Non-inheriting extensions of asyncio.Queue with more methods and password protection, and a PotentQueueBase ABC.

Attributes

ignore_qempty

Instance of IgnoreErrors that suppresses QueueShutDown and QueueEmpty.

ignore_qerrs

Instance of IgnoreErrors that suppresses all asyncio queue-related errors.

ignore_qfull

Instance of IgnoreErrors that suppresses QueueShutDown and QueueFull.

ignore_qshutdown

Instance of IgnoreErrors that suppresses QueueShutDown.

Classes

PotentQueueBase

A base class for queues with much more methods, async- and sync-compatible.

SmartLifoQueue

A base class for queues with much more methods, async- and sync-compatible.

SmartPriorityQueue

A priority queue, where the priority of each item is determined by comparing it to other items, meaning each item should at least implement __lt__().

SmartQueue

A base class for queues with much more methods, async- and sync-compatible.

UserPriorityQueue

Functions
Module Contents
class asyncutils.queues.PotentQueueBase[T]

Bases: asyncio.Queue[T], asyncutils._internal.helpers.LoopMixinBase, abc.ABC

A base class for queues with much more methods, async- and sync-compatible.

__aiter__() types.AsyncGeneratorType[T]

Equivalent to drain_persistent().

__bool__() bool

Whether there are items in the queue.

__iter__() types.GeneratorType[T]

Equivalent to drain_until_empty().

abstractmethod _get() T

Get an item from the queue if not empty; called by get() and get_nowait().

abstractmethod _init(maxsize: int) None

Initialize the queue given maxsize.

abstractmethod _put(item: T) None

Put an item into the queue if not empty; called by put() and put_nowait().

clear() None

Remove all the entries from the queue.

drain_into_list(max_items: int | None = ...) list[T]

Empty the queue and return a list of the items within.

drain_persistent(max_items: int | None = ..., timeout: float | None = ...) types.AsyncGeneratorType[T]

Get items from the queue once available and yield them.

drain_until_empty(max_items: int | None = ...) types.GeneratorType[T]

Get and yield items from the queue synchronously until it is emptied.

empty() bool

Whether the queue is empty.

enumerate(*, lifo: Literal[False] = ...) SmartQueue[tuple[int, T]]
enumerate(*, lifo: Literal[True]) SmartLifoQueue[tuple[int, T]]

Return a queue containing the items from enumerate applied on this queue and empty it in the process.

enumerate_nowait(start: int = ..., *, step: int = ...) types.GeneratorType[tuple[int, T]]

Do the equivalent of zipping itertools.count(start, step) with the items of the queue. When the returned generator is advanced and the queue is empty at that moment, the generator stops entirely.

async extend(it: asyncutils._internal.prots.SupportsIteration[T]) None

Add the items from it into the queue.

filter(pred: collections.abc.Callable[[T], bool] = ..., *, lifo: Literal[False] = ...) SmartQueue[T]
filter(pred: collections.abc.Callable[[T], bool] = ..., *, lifo: Literal[True]) SmartLifoQueue[T]

Return a new queue from which getters can get the items in this queue that satisfy the predicate; items remaining in the original queue did not satisfy the predicate.

filter_nowait(pred: collections.abc.Callable[[T], bool] = ..., /) tuple[list[T], int]

Filter items in the queue by a predicate and return a list of removed items and an integer; the items in the returned list after the index corresponding to that integer were items rejected from the queue due to the queue being full.

map[R](
f: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
stop_when: asyncio.Future[None] | None = ...,
*,
lifo: Literal[False] = ...,
) SmartQueue[R]
map(
f: collections.abc.Callable[[T], collections.abc.Awaitable[R]],
stop_when: asyncio.Future[None] | None = ...,
*,
lifo: Literal[True],
) SmartLifoQueue[R]

Return a queue that contains items from this queue with the function applied on each of them, emptying this queue in the process (transformation analogous to map).

abstractmethod peek_all() list[T]

Return a list of all the items in the queue.

async poppush(item: T) T

poppush_nowait(), but done asynchronously and not immediately.

poppush_nowait(item: T, raising: bool = ...) T

Pop an item from the queue and push into the other end immediately.

push(item: T) bool

Put an item into the queue immediately, popping if necessary; returns success.

async pushpop(item: T) T

pushpop_nowait(), but done asynchronously and not immediately.

pushpop_nowait(item: T, raising: bool = ...) T

Push an item into the queue and pop from the other end immediately.

abstractmethod qsize() int

Return the size of the queue as an integer.

reset() None

Revert the queue to an empty state.

shutdown(immediate: bool = ...) None

Shut down the queue. If immediate is True, pending gets raise immediately even if the queue is not empty.

async smart_get(*, timeout: float | None = ..., default: T = ...) T

Call get_nowait() if an item is immediately available, waiting for a item with timeout otherwise; if the timeout expires and default is provided, return it.

async smart_put(item: T, *, timeout: float | None = ..., raising: bool = ...) bool

Put item into the queue. Return True if a slot is immediately available, waiting for a slot with timeout otherwise; if the timeout expires and raising is True, throw TimeoutError.

starmap[R, *Ts](
f: collections.abc.Callable[[*Ts], collections.abc.Awaitable[R]],
stop_when: asyncio.Future[None] | None = ...,
*,
lifo: Literal[False] = ...,
) SmartQueue[R]
starmap(
f: collections.abc.Callable[[*Ts], collections.abc.Awaitable[R]],
stop_when: asyncio.Future[None] | None = ...,
*,
lifo: Literal[True],
) SmartLifoQueue[R]

Return a queue that contains items from this queue with the function applied on each of them starred, emptying this queue in the process (transformation analogous to itertools.starmap()).

transaction() contextlib.AbstractContextManager[Self, None]
Return an async context manager which begins a transaction on entry.
If an error occurs within the context, the original items in the queue are restored and the error re-raised, unless the error is critical
and deemed to require immediate exit. Otherwise, the transaction completes successfully and changes are committed on exit.
property can_get_now: bool

Whether items can be get from the queue without blocking at this instant.

property can_put_now: bool

Whether items can be put into the queue without blocking at this instant.

property capacity: int

The capacity of the queue. Can be math.inf.

property fully_functional: bool

queue.fully_functional == queue.can_put_now and queue.can_get_now.

property is_shutdown: bool

Whether the queue is shutting down or has been shutdown.

property remaining_capacity: int

The remaining number of slots in the queue. Can be math.inf.

property utilization_rate: float

The number of items the queue divided by its capacity.

class asyncutils.queues.SmartLifoQueue[T]

Bases: PotentQueueBase[T]

A base class for queues with much more methods, async- and sync-compatible.

_get() T

Get an item from the queue if not empty; called by get() and get_nowait().

_init(maxsize: int) None

Initialize the queue given maxsize.

_put(item: T) None

Put an item into the queue if not empty; called by put() and put_nowait().

peek(i: int = ..., /) T

Look at the item at index i, defaulting to the item most recently put in (that would be returned by get() or get_nowait()).

peek_all() list[T]

Return a list of all the items in the queue.

qsize() int

Return the size of the queue as an integer.

class asyncutils.queues.SmartPriorityQueue[T](maxsize: int = ..., *, init_items: asyncutils._internal.prots.SupportsIteration[T])
class asyncutils.queues.SmartPriorityQueue(maxsize: int = ...)

Bases: PotentQueueBase[T]

A priority queue, where the priority of each item is determined by comparing it to other items, meaning each item should at least implement __lt__().

_get() T

Get an item from the queue if not empty; called by get() and get_nowait().

_init(maxsize: int) None

Initialize the queue given maxsize.

_put(item: T) None

Put an item into the queue if not empty; called by put() and put_nowait().

peek() T

Look at the item that would be returned by get() or get_nowait() without actually removing it from the queue.

peek_all() list[T]

Return a list of all the items in the queue.

qsize() int

Return the size of the queue as an integer.

async start(maxsize: int, init_items: asyncutils._internal.prots.SupportsIteration[T]) None
class asyncutils.queues.SmartQueue[T]

Bases: PotentQueueBase[T]

A base class for queues with much more methods, async- and sync-compatible.

_get() T

Get an item from the queue if not empty; called by get() and get_nowait().

_init(maxsize: int) None

Initialize the queue given maxsize.

_put(item: T) None

Put an item into the queue if not empty; called by put() and put_nowait().

peek() T

Look at the item that would be returned by get() or get_nowait() without actually removing it from the queue.

peek_all() list[T]

Return a list of all the items in the queue.

qsize() int

Return the size of the queue as an integer.

rotate(n: int = ..., /) None

Rotate the items in the queue by n indices synchronously, which can be negative.

class asyncutils.queues.UserPriorityQueue[T](
maxsize: int = ...,
*,
init_priority: int = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
)
class asyncutils.queues.UserPriorityQueue(maxsize: int = ..., *, init_priority: int = ...)

Bases: SmartPriorityQueue[tuple[int, int, T]]

A priority queue, where you put in items with an integer priority and the items are retrieved in ascending order of priority, with earlier
items taking precedence in case of ties.
The put() and put_nowait() methods of this class take an additional priority parameter, representing the priority of the item.
classmethod from_iter_of_tuples(items: asyncutils._internal.prots.SupportsIteration[tuple[int, int, T]], maxsize: int = ...) Self

Build a queue from the (async) iterable of tuples (priority, tiebreak, item).

async get() T
get_nowait() T
async put(item: T, priority: int = ...) None
put_nowait(item: T, priority: int = ...) None
asyncutils.queues.password_queue[T, R](
password_put: R,
*,
maxsize: int = ...,
protect_get: Literal[False] = ...,
protect_put: Literal[True] = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
puttyp: type[R] = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.PutProtectedQProtocol[R, T]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[False] = ...,
protect_put: Literal[True] = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
put_from: str = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.PutProtectedQProtocol[Any, T]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[False] = ...,
protect_put: Literal[True] = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
put_from: str = ...,
puttyp: type[R],
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.PutProtectedQProtocol[R, T]
asyncutils.queues.password_queue(
*,
password_get: R,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[False],
can_change_get: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
gettyp: type[R] = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetProtectedQProtocol[R, T]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[False],
can_change_get: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
gettyp: type[R],
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetProtectedQProtocol[R, T]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[False],
can_change_get: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetProtectedQProtocol[Any, T]
asyncutils.queues.password_queue(
password_put: V,
password_get: R,
maxsize: int = ...,
*,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
gettyp: type[R] = ...,
puttyp: type[V] = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, V, T]
asyncutils.queues.password_queue(
password_put: V,
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
gettyp: type[R],
puttyp: type[V] = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, V, T]
asyncutils.queues.password_queue(
password_put: V,
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
puttyp: type[V] = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[Any, V, T]
asyncutils.queues.password_queue(
*,
password_get: R,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
put_from: str = ...,
gettyp: type[R] = ...,
puttyp: type[V],
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, V, T]
asyncutils.queues.password_queue(
*,
password_get: R,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
put_from: str = ...,
gettyp: type[R] = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, Any, T]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
put_from: str = ...,
gettyp: type[R],
puttyp: type[V],
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, V, T]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
put_from: str = ...,
gettyp: type[R],
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, Any, T]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
put_from: str = ...,
puttyp: type[V],
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[Any, V, T]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
put_from: str = ...,
init_items: asyncutils._internal.prots.SupportsIteration[T],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[Any, Any, T]
asyncutils.queues.password_queue(
password_put: R,
*,
maxsize: int = ...,
protect_get: Literal[False] = ...,
protect_put: Literal[True] = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
puttyp: type[R] = ...,
strict: bool = ...,
) asyncutils._internal.prots.PutProtectedQProtocol[R, Any]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[False] = ...,
protect_put: Literal[True] = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
put_from: str = ...,
puttyp: type[R],
strict: bool = ...,
) asyncutils._internal.prots.PutProtectedQProtocol[R, Any]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[False] = ...,
protect_put: Literal[True] = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
put_from: str = ...,
strict: bool = ...,
) asyncutils._internal.prots.PutProtectedQProtocol[Any, Any]
asyncutils.queues.password_queue(
*,
password_get: R,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[False],
can_change_get: bool = ...,
priority: bool = ...,
lifo: bool = ...,
gettyp: type[R] = ...,
strict: bool = ...,
) asyncutils._internal.prots.GetProtectedQProtocol[R, Any]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[False],
can_change_get: bool = ...,
priority: bool = ...,
lifo: bool = ...,
gettyp: type[R],
strict: bool = ...,
) asyncutils._internal.prots.GetProtectedQProtocol[R, Any]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[False],
can_change_get: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
strict: bool = ...,
) asyncutils._internal.prots.GetProtectedQProtocol[Any, Any]
asyncutils.queues.password_queue(
password_put: V,
password_get: R,
maxsize: int = ...,
*,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
gettyp: type[R] = ...,
puttyp: type[V] = ...,
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, V, Any]
asyncutils.queues.password_queue(
password_put: V,
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
gettyp: type[R],
puttyp: type[V] = ...,
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, V, Any]
asyncutils.queues.password_queue(
password_put: V,
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
puttyp: type[V] = ...,
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[Any, V, Any]
asyncutils.queues.password_queue(
*,
password_get: R,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
put_from: str = ...,
gettyp: type[R] = ...,
puttyp: type[V],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, V, Any]
asyncutils.queues.password_queue(
*,
password_get: R,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
put_from: str = ...,
gettyp: type[R] = ...,
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, Any, Any]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
put_from: str = ...,
gettyp: type[R],
puttyp: type[V],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, V, Any]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
put_from: str = ...,
gettyp: type[R],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[R, Any, Any]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
put_from: str = ...,
puttyp: type[V],
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[Any, V, Any]
asyncutils.queues.password_queue(
*,
maxsize: int = ...,
protect_get: Literal[True],
protect_put: Literal[True] = ...,
can_change_get: bool = ...,
can_change_put: bool = ...,
priority: bool = ...,
lifo: bool = ...,
get_from: str = ...,
put_from: str = ...,
strict: bool = ...,
) asyncutils._internal.prots.GetAndPutProtectedQProtocol[Any, Any, Any]
Return a thread-unsafe password-protected queue, the type of which does not inherit from asyncio.Queue but has the same interface.
The queue has maximum size maxsize. priority and lifo parameters determine if the queue is a priority queue and last-in-first-out.
If protect_get is True, get and get_nowait will require a password, specified by password_get or retrieved from a variable in the caller’s scope with name get_from (default :const`context.PASSWORD_QUEUE_DEFAULT_GET_FROM`).
If protect_put is True, put and put_nowait will require a password, specified by password_put or retrieved from a variable in the caller’s scope with name put_from (default :const`context.PASSWORD_QUEUE_DEFAULT_PUT_FROM`).
If init_items is specified, the items in that (async) iterable will be arranged to enter the queue eventually.

Danger

This function is meant not for cryptographic purposes, because no hashing of the password is performed! Attackers may obtain sensitive information, namely the passwords used by the queue, from the memory address of the returned object alone, or worse still, access and modify the internal stack/queue storing the items directly. Put more bluntly, the password protection offered is purely cosmetic.

Note

The excessive amount of overloads here cannot be helped due to accurate typing needs. When we drop support for Python 3.12, we will use default values in the type parameters here to cut this number in half.

Note

The overloads do not cover the technically valid but useless case with both protect_get and protect_put being False.

Note

Little type validation for the argument combinations is done at runtime; it is hoped that type checkers will catch most misuses.

asyncutils.queues.ignore_qempty: Final[asyncutils.exceptions.IgnoreErrors]

Instance of IgnoreErrors that suppresses QueueShutDown and QueueEmpty.

asyncutils.queues.ignore_qerrs: Final[asyncutils.exceptions.IgnoreErrors]

Instance of IgnoreErrors that suppresses all asyncio queue-related errors.

asyncutils.queues.ignore_qfull: Final[asyncutils.exceptions.IgnoreErrors]

Instance of IgnoreErrors that suppresses QueueShutDown and QueueFull.

asyncutils.queues.ignore_qshutdown: Final[asyncutils.exceptions.IgnoreErrors]

Instance of IgnoreErrors that suppresses QueueShutDown.

asyncutils.rwlocks

Readers-writer locks with different fairness policies, applicable in different situations.

Classes

AgingRWLock

A readers-writer lock with a priority policy multiplying the current number of attempts to acquire the reading or writing lock, counted per corresponding task, by the respective factor given at construction, to obtain the priority.

CoercedMethod

Interpret any callable as a regular function in a class body so that access on instance returns something like a bound method.

FairPriorityRWLock

At the same priority level, writers are preferred over readers.

FairRWLock

Readers-writer lock that maintains FIFO order for both readers and writers indiscriminately.

PriorityRWLock

RWLock

ReadPreferredRWLock

Readers-writer lock preferring readers. This risks writer starvation, which becomes less of an issue if there are only a few readers.

WritePreferredPriorityRWLock

Writers at any priority level are preferred over readers at any priority level.

WritePreferredRWLock

Readers-writer lock preferring writers. This risks reader starvation, which becomes less of an issue if there are only a few writers.

Module Contents
class asyncutils.rwlocks.AgingRWLock

Bases: PriorityRWLock

A readers-writer lock with a priority policy multiplying the current number of attempts to acquire the reading or writing lock, counted per corresponding task, by the respective factor given at construction, to obtain the priority.

reading(priority: int = ...) asyncutils._internal.prots.RWLockCM

Return an async context manager for reading access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

setup() None

Set up the internal state of the lock.

writing(priority: int = ...) asyncutils._internal.prots.RWLockCM

Return an async context manager for writing access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

property cur_unsuccessful_reads: int

The current number of unsuccessful attempts to acquire the reading lock, counted across all tasks.

property cur_unsuccessful_writes: int

The current number of unsuccessful attempts to acquire the writing lock, counted across all tasks.

class asyncutils.rwlocks.CoercedMethod[T, R, **P](func: collections.abc.Callable[Concatenate[R, P], T], /)

Interpret any callable as a regular function in a class body so that access on instance returns something like a bound method.

__get__(instance: R, owner: type[R] | None = ..., /) collections.abc.Callable[P, T]

Return the ‘bound method’. The descriptor itself cannot be directly accessed on the class it is defined in, only instances of.

__getattr__(name: str, /) Any
__set_name__(owner: type[R], name: str, /) None
class asyncutils.rwlocks.FairPriorityRWLock

Bases: PriorityRWLock

At the same priority level, writers are preferred over readers.

Whether instantiating this class gives a PriorityRWLock unfair to readers by default depends on RWLOCK_DEFAULT_PREFER_WRITERS.

class asyncutils.rwlocks.FairRWLock

Bases: RWLock

Readers-writer lock that maintains FIFO order for both readers and writers indiscriminately.

Return a WritePreferredRWLock if prefer_writers is True, otherwise a ReadPreferredRWLock. RWLOCK_DEFAULT_PREFER_WRITERS becomes the value of prefer_writers when it is not passed.

reading() asyncutils._internal.prots.RWLockCM

Return an async context manager for reading access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

setup() None

Set up the internal state of the lock.

writing() asyncutils._internal.prots.RWLockCM

Return an async context manager for writing access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

class asyncutils.rwlocks.PriorityRWLock

Bases: RWLock

Lower priority levels are preferred, and the default priority is 0, as in other patterns in this module related to priority.

Whether instantiating this class gives a PriorityRWLock unfair to readers by default depends on RWLOCK_DEFAULT_PREFER_WRITERS.

reading(priority: int = ...) asyncutils._internal.prots.RWLockCM

Return an async context manager for reading access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

setup() None

Set up the internal state of the lock.

writing(priority: int = ...) asyncutils._internal.prots.RWLockCM

Return an async context manager for writing access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

class asyncutils.rwlocks.RWLock

Bases: abc.ABC

Common base class for all readers-writer locks.
If you would like to subclass this, you must implement reading(), writing() and setup().

Return a WritePreferredRWLock if prefer_writers is True, otherwise a ReadPreferredRWLock. RWLOCK_DEFAULT_PREFER_WRITERS becomes the value of prefer_writers when it is not passed.

is_reading() bool

Whether the lock is currently held by a reader. Default implementation returns whether the _nr attribute is greater than 0, assuming that slot holds the number of readers.

is_writing() bool

Whether the lock is currently held by a writer. Default implementation returns the value of the _wa attribute.

classmethod lock[T, **P](f: collections.abc.Callable[P, collections.abc.Awaitable[T]], /) asyncutils._internal.prots.RWLockRV[T, P]

Create a lock and register a reader.

locked() bool

Return False iff a writer can enter at this moment.

reader[T, **P](f: collections.abc.Callable[P, collections.abc.Awaitable[T]], /) asyncutils._internal.prots.RWLockRV[T, P]

Return a decorator wrapping a function returning an awaitable in an async reading context. reader() and writer() methods are attached to the returned async callable.

abstractmethod reading() asyncutils._internal.prots.RWLockCM

Return an async context manager for reading access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

abstractmethod setup() None

Set up the internal state of the lock.

writer[T, **P](f: collections.abc.Callable[P, collections.abc.Awaitable[T]], /) asyncutils._internal.prots.RWLockRV[T, P]

Return a decorator wrapping a function returning an awaitable in an async writing context. reader() and writer() methods are attached to the returned async callable.

abstractmethod writing() asyncutils._internal.prots.RWLockCM

Return an async context manager for writing access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

class asyncutils.rwlocks.ReadPreferredRWLock

Bases: RWLock

Readers-writer lock preferring readers. This risks writer starvation, which becomes less of an issue if there are only a few readers.

Return a WritePreferredRWLock if prefer_writers is True, otherwise a ReadPreferredRWLock. RWLOCK_DEFAULT_PREFER_WRITERS becomes the value of prefer_writers when it is not passed.

is_reading() bool

Whether the lock is currently held by a reader. Default implementation returns whether the _nr attribute is greater than 0, assuming that slot holds the number of readers.

is_writing() bool

Whether the lock is currently held by a writer. Default implementation returns the value of the _wa attribute.

locked() bool

Return False iff a writer can enter at this moment.

reading() asyncutils._internal.prots.RWLockCM

Return an async context manager for reading access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

setup() None

Set up the internal state of the lock.

writing() asyncutils._internal.prots.RWLockCM

Return an async context manager for writing access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

class asyncutils.rwlocks.WritePreferredPriorityRWLock

Bases: PriorityRWLock

Writers at any priority level are preferred over readers at any priority level.

Whether instantiating this class gives a PriorityRWLock unfair to readers by default depends on RWLOCK_DEFAULT_PREFER_WRITERS.

class asyncutils.rwlocks.WritePreferredRWLock

Bases: RWLock

Readers-writer lock preferring writers. This risks reader starvation, which becomes less of an issue if there are only a few writers.

Return a WritePreferredRWLock if prefer_writers is True, otherwise a ReadPreferredRWLock. RWLOCK_DEFAULT_PREFER_WRITERS becomes the value of prefer_writers when it is not passed.

reading() asyncutils._internal.prots.RWLockCM

Return an async context manager for reading access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

setup() None

Set up the internal state of the lock.

writing() asyncutils._internal.prots.RWLockCM

Return an async context manager for writing access. It is recommended to implement this by decorating an async generator function with contextlib.asynccontextmanager().

asyncutils.signals

Functions related to asynchronous signal handling.

Functions
Module Contents
async asyncutils.signals.wait_for_signal[T](
processor: collections.abc.Callable[[signal.Signals], collections.abc.Awaitable[T]],
/,
*S: int,
timeout: float | None = ...,
raise_on_timeout: Literal[True],
loop: asyncio.AbstractEventLoop | None = ...,
possible_errors: tuple[asyncutils._internal.prots.ExcType, Ellipsis] = ...,
default_on_processor_failure: T,
sigs: collections.abc.Iterable[int] = ...,
logger: logging.Logger = ...,
) T
async asyncutils.signals.wait_for_signal(
processor: collections.abc.Callable[[signal.Signals], collections.abc.Awaitable[T]],
/,
*S: int,
timeout: float | None = ...,
raise_on_timeout: Literal[True],
loop: asyncio.AbstractEventLoop | None = ...,
possible_errors: tuple[asyncutils._internal.prots.ExcType, Ellipsis] = ...,
sigs: collections.abc.Iterable[int] = ...,
logger: logging.Logger = ...,
) T | None
async asyncutils.signals.wait_for_signal(
processor: collections.abc.Callable[[signal.Signals], collections.abc.Awaitable[T]],
/,
*S: int,
timeout: float | None = ...,
raise_on_timeout: Literal[False] = ...,
loop: asyncio.AbstractEventLoop | None = ...,
possible_errors: tuple[asyncutils._internal.prots.ExcType, Ellipsis] = ...,
sigs: collections.abc.Iterable[int] = ...,
logger: logging.Logger = ...,
) T | None
async asyncutils.signals.wait_for_signal(
processor: collections.abc.Callable[[signal.Signals], collections.abc.Awaitable[T]],
/,
*S: int,
timeout: float | None = ...,
raise_on_timeout: Literal[False] = ...,
loop: asyncio.AbstractEventLoop | None = ...,
possible_errors: tuple[asyncutils._internal.prots.ExcType, Ellipsis] = ...,
default_on_processor_failure: T,
sigs: collections.abc.Iterable[int] = ...,
logger: logging.Logger = ...,
) T | None
async asyncutils.signals.wait_for_signal(
processor: collections.abc.Callable[[signal.Signals], T],
/,
*S: int,
timeout: float | None = ...,
raise_on_timeout: Literal[True],
loop: asyncio.AbstractEventLoop | None = ...,
possible_errors: tuple[asyncutils._internal.prots.ExcType, Ellipsis] = ...,
default_on_processor_failure: T,
sigs: collections.abc.Iterable[int] = ...,
logger: logging.Logger = ...,
) T
async asyncutils.signals.wait_for_signal(
processor: collections.abc.Callable[[signal.Signals], T],
/,
*S: int,
timeout: float | None = ...,
raise_on_timeout: Literal[True],
loop: asyncio.AbstractEventLoop | None = ...,
possible_errors: tuple[asyncutils._internal.prots.ExcType, Ellipsis] = ...,
sigs: collections.abc.Iterable[int] = ...,
logger: logging.Logger = ...,
) T | None
async asyncutils.signals.wait_for_signal(
processor: collections.abc.Callable[[signal.Signals], T],
/,
*S: int,
timeout: float | None = ...,
raise_on_timeout: Literal[False] = ...,
loop: asyncio.AbstractEventLoop | None = ...,
possible_errors: tuple[asyncutils._internal.prots.ExcType, Ellipsis] = ...,
sigs: collections.abc.Iterable[int] = ...,
logger: logging.Logger = ...,
) T | None
async asyncutils.signals.wait_for_signal(
processor: collections.abc.Callable[[signal.Signals], T],
/,
*S: int,
timeout: float | None = ...,
raise_on_timeout: Literal[False] = ...,
loop: asyncio.AbstractEventLoop | None = ...,
possible_errors: tuple[asyncutils._internal.prots.ExcType, Ellipsis] = ...,
default_on_processor_failure: T,
sigs: collections.abc.Iterable[int] = ...,
logger: logging.Logger = ...,
) T | None
Wait for an operating system level signal included in sigs (default WAIT_FOR_SIGNAL_DEFAULT_SIGNALS) and the variable positional arguments to be signalled within timeout and handle it.
See the docs for the signal module, add_signal_handler(), as well as the Wikipedia page for signals.
processor should be a function that takes the signal occurred, preferably returning an awaitable object.
If raise_on_timeout is True, throw TimeoutError on timeout. Otherwise, return None.
If loop is passed, its add_signal_handler() and remove_signal_handler() methods will be used; a loop is created and set otherwise.
Errors whose types are included in possible_errors will cause the logger logger to emit an error and the function to return default_on_processor_failure, or None if not passed. Some information related to the progress of the wait also goes to logger.
The return value of the processor is returned through this function.
Note

There is limited support for signals on Windows and this function may not work as expected even with the little signals it provides. Therefore, the function emits a warning unless the console is running, in which case it would be much too annoying.

asyncutils.tools

Utilities related to the command-line interface and getting metadata for package configuration.

Functions

argstr_to_json(→ None)

Parse the shell-escaped string representing the command-line arguments for this module and writes it into a .json path.

argv_to_json(→ None)

find_help_url(→ str)

Get the URL of the asyncutils documentation page for obj. See the supported calling patterns here.

get_cfg_json_format(→ str)

get_cmd_help(→ str)

Return the command line help as a string containing ANSI colour escape sequences.

json_to_argstr(→ str)

Essentially the output of json_to_argv(), but joined into a shell-escaped string with join.

json_to_argv(→ list[str])

loadf(→ dict[str, Any])

Load the file at path, with the specified file extension if undeducible from the file name, into a dictionary using the correct library.

open_help(→ bool)

Open the URL to the documentation of the specified symbol defined in asyncutils via the default browser, returning success.

print_cfg_json_format(→ None)

Print the format, as gotten by get_cfg_json_format(), into the specified file and flush it (default stdout).

print_cmd_help(→ None)

Print the help, as returned by get_cmd_help(), into the specified file (default stdout) and flush it.

Module Contents
asyncutils.tools.argstr_to_json(
argstr: str,
path: asyncutils._internal.prots.Openable,
/,
*,
dump: asyncutils._internal.prots.DumpType = ...,
split: collections.abc.Callable[[str], collections.abc.Sequence[str]] = ...,
) None

Parse the shell-escaped string representing the command-line arguments for this module and writes it into a .json path.

asyncutils.tools.argv_to_json(
argv: collections.abc.Sequence[str],
path: asyncutils._internal.prots.Openable,
/,
*,
dump: asyncutils._internal.prots.DumpType = ...,
) None
Writes the sequence of strings, parsed as command-line arguments for this module, into path in JSON format.
Since this function is ‘environment-agnostic’, it may have unintended behaviour if the arguments passed rely on current configuration, which is not captured.
asyncutils.tools.find_help_url(obj: object = ..., /) str

Get the URL of the asyncutils documentation page for obj. See the supported calling patterns here.

Caution

The URL returned is not guaranteed to work with strings representing non-existent, undocumented or internal symbols.

asyncutils.tools.get_cfg_json_format() str
Get the format of .json configs this module takes as a string.
print_cfg_json_format() is perhaps more useful.
If you would like a format schema for other languages, a programmatic approach would likely be unnecessary; you can just use an online tool implementing a browser-based converter.
asyncutils.tools.get_cmd_help() str

Return the command line help as a string containing ANSI colour escape sequences.

Implementation detail

This is actually a bound method of the library’s argument parser at runtime.

asyncutils.tools.json_to_argstr(
path: asyncutils._internal.prots.Openable,
/,
*,
join: collections.abc.Callable[[list[str]], str] = ...,
) str

Essentially the output of json_to_argv(), but joined into a shell-escaped string with join.

asyncutils.tools.json_to_argv(path: asyncutils._internal.prots.Openable, /) list[str]
Return a list of strings representing the command-line arguments for this module from path to the corresponding json file, with as little items as possible.
For integer file descriptors as path, the format is assumed to be plain JSON.
The module should have a load function that takes path and returns a dict of its contents.
Perfect round-trip conversion with argv_to_json() is guaranteed only with no other configuration file active.
asyncutils.tools.loadf(path: asyncutils._internal.prots.Openable, ext: str = ..., /) dict[str, Any]

Load the file at path, with the specified file extension if undeducible from the file name, into a dictionary using the correct library.

asyncutils.tools.open_help(obj: object = ..., /) bool

Open the URL to the documentation of the specified symbol defined in asyncutils via the default browser, returning success.

asyncutils.tools.print_cfg_json_format(file: asyncutils._internal.prots.CanWriteAndFlush[str] = ..., *, flush: bool = ...) None

Print the format, as gotten by get_cfg_json_format(), into the specified file and flush it (default stdout).

asyncutils.tools.print_cmd_help(file: asyncutils._internal.prots.CanWriteAndFlush[str] = ..., *, flush: bool = ...) None

Print the help, as returned by get_cmd_help(), into the specified file (default stdout) and flush it.

asyncutils.util

Functions of utility one tier below base, such that they are not worth preloading but still quite useful.

Attributes

anullcontext

An instance of an async context manager that does nothing.

ignore_cancellation

Context manager to ignore CancelledError.

Functions

aawcmf2dcmf(→ collections.abc.Callable[P, ...)

Equivalent to aawcmf2dcmff()(f).

aawcmf2dcmff(...)

Return a decorator converting a function giving an awaitable resolving to an async context manager into a function returning a non-reusable dual context manager using dualcontextmanager().

afalsify(→ Literal[False])

Do nothing and return False.

afcopy(→ collections.abc.Callable[P, ...)

Return a copy of the async function f with the same signature and attributes.

aiter_from_f(→ types.AsyncGeneratorType[T])

Emulate the second form of the builtin iter() function in async, which the aiter() function does not have.

anullify(→ None)

Do nothing and return None.

atruthify(→ Literal[True])

Do nothing and return True.

avalify(→ collections.abc.Callable[Ellipsis, ...)

Return an async function that takes any arguments, always returning the value v.

dcm(→ collections.abc.Callable[P, ...)

Equivalent to dualcontextmanager() with the default arguments at the time of definition, rather than when the function is decorated.

discard_retval(→ collections.abc.Callable[P, ...)

Return an async function with the same signature as f that awaits the result of f and discards it.

done_evt(…)

Return a new async event that is already set, with type evtcls if passed and asyncio.Event by default.

done_fut(…)

Return a future that is already done with the result res or the exception wrapped by the wrapper exc if it is an exception wrapper returned by wrap_exc(), with type futcls if passed and asyncio.Future by default.

dualcontextmanager(…)

Convert a callable that returns an (async) iterable, usually an (async) generator function, over exactly one item, into a function returning a non-reusable sync- and async-compatible context manager. Essentially combines contextlib.contextmanager() and contextlib.asynccontextmanager() into one decorator.

evaluate_and_return(→ collections.abc.Callable[P, ...)

Return an async function with the same signature as f that awaits the result of f and returns r.

get_future(→ asyncio.Future[T])

locked_lock(…)

Return an already acquired lock of type lcls if passed and asyncio.Lock by default.

lockf(→ collections.abc.Callable[P, ...)

Apply a lock that implements the async lock interface, as constructed and returned by lf, to a function f that returns an awaitable, also converting it to an async function.

make_task_factory(...)

Return a task factory accepted by set_task_factory() that creates tasks of type tcls with the eager_start argument set to eager, its default value being MAKE_TASK_FACTORY_DEFAULT_EAGER.

new_eager_tasks(→ types.GeneratorType[asyncio.Task[T]])

Yield eagerly started tasks wrapping the coroutines under the running loop (or a new one that is set as the current if required) in order.

safe_cancel(→ None)

semaphore(…)

Return a (bounded) semaphore of value workers, defaulting to SEMAPHORE_DEFAULT_VALUE.

sync_await(→ T)

Await the awaitable object aw under the given event loop loop with timeout timeout synchronously. If never_block=False is passed and the loop is not running, its run_until_complete() method may be called; otherwise, a pair of futures is created to coordinate the execution of the awaitable. It is preferred to use asyncio.run() to synchronously run one single top-level async function that awaits the necessary awaitables. Calling this function with the event loop running in the current thread will cause RuntimeError to be thrown.

to_async(→ collections.abc.Callable[P, ...)

to_sync(→ collections.abc.Callable[P, T])

Convert a function that returns an awaitable to an sync function with the same signature, using the event loop loop when required or creating when necessary.

to_sync_from_loop(...)

Return the partial of to_sync() under loop=loop.

transient_block(…)

transient_block_from_loop(...)

Return the partial of transient_block() under the specified loop.

wrap_in_coro(→ T)

Return a coroutine resolving to the result of the awaitable aw, such that it can be passed to asyncio.create_task().

Module Contents
asyncutils.util.aawcmf2dcmf[T, **P](
f: collections.abc.Callable[P, collections.abc.Awaitable[contextlib.AbstractContextManager[T] | contextlib.AbstractAsyncContextManager[T]]],
/,
) collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]

Equivalent to aawcmf2dcmff()(f).

asyncutils.util.aawcmf2dcmff[
T,
**P,
](
*,
use_existing_executor: bool = ...,
create_executor: bool = ...,
strict: bool = ...,
) collections.abc.Callable[[collections.abc.Callable[P, collections.abc.Awaitable[contextlib.AbstractContextManager[T] | contextlib.AbstractAsyncContextManager[T]]]], collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]]

Return a decorator converting a function giving an awaitable resolving to an async context manager into a function returning a non-reusable dual context manager using dualcontextmanager().

async asyncutils.util.afalsify(*a: object, **k: object) Literal[False]

Do nothing and return False.

asyncutils.util.afcopy[T, **P](
f: collections.abc.Callable[P, collections.abc.Awaitable[T]],
/,
) collections.abc.Callable[P, types.CoroutineType[Any, Any, T]]

Return a copy of the async function f with the same signature and attributes.

asyncutils.util.aiter_from_f[T](
f: collections.abc.Callable[[], collections.abc.Awaitable[T]],
sentinel: T = ...,
/,
*,
yield_sentinel: bool = ...,
) types.AsyncGeneratorType[T]

Emulate the second form of the builtin iter() function in async, which the aiter() function does not have.

async asyncutils.util.anullify(*a: object, **k: object) None

Do nothing and return None.

async asyncutils.util.atruthify(*a: object, **k: object) Literal[True]

Do nothing and return True.

asyncutils.util.avalify[T](v: T, /) collections.abc.Callable[Ellipsis, types.CoroutineType[Any, Any, T]]

Return an async function that takes any arguments, always returning the value v.

asyncutils.util.dcm[T, **P](
f: collections.abc.Callable[P, asyncutils._internal.prots.SupportsIteration[T]],
/,
) collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]

Equivalent to dualcontextmanager() with the default arguments at the time of definition, rather than when the function is decorated.

asyncutils.util.discard_retval[T, **P](
f: collections.abc.Callable[P, collections.abc.Awaitable[T]],
/,
) collections.abc.Callable[P, types.CoroutineType[Any, Any, None]]

Return an async function with the same signature as f that awaits the result of f and discards it.

asyncutils.util.done_evt[T: asyncutils._internal.prots.EventProtocol](*, evtcls: type[T]) T
asyncutils.util.done_evt() asyncio.Event

Return a new async event that is already set, with type evtcls if passed and asyncio.Event by default.

asyncutils.util.done_fut(
exc: asyncutils._internal.prots.ExceptionWrapper,
/,
*,
futcls: type[asyncutils._internal.prots.FutProtocol[Any]],
) asyncutils._internal.prots.IncompleteFut[Never]
asyncutils.util.done_fut(
res: None = ...,
*,
futcls: type[asyncutils._internal.prots.FutProtocol[Any]],
) asyncutils._internal.prots.IncompleteFut[None]
asyncutils.util.done_fut(
res: T,
*,
futcls: type[asyncutils._internal.prots.FutProtocol[Any]],
) asyncutils._internal.prots.IncompleteFut[T]
asyncutils.util.done_fut(exc: asyncutils._internal.prots.ExceptionWrapper, /) asyncio.Future[Never]
asyncutils.util.done_fut(res: None = ...) asyncio.Future[None]
asyncutils.util.done_fut(res: T) asyncio.Future[T]

Return a future that is already done with the result res or the exception wrapped by the wrapper exc if it is an exception wrapper returned by wrap_exc(), with type futcls if passed and asyncio.Future by default.

asyncutils.util.dualcontextmanager[
T,
**P,
](
*,
use_existing_executor: bool,
strict: Literal[True],
) collections.abc.Callable[[collections.abc.Callable[P, collections.abc.Iterable[T]]], collections.abc.Callable[P, contextlib.AbstractContextManager[T, bool]]]
asyncutils.util.dualcontextmanager(
*,
create_executor: bool,
strict: Literal[True],
) collections.abc.Callable[[collections.abc.Callable[P, collections.abc.Iterable[T]]], collections.abc.Callable[P, contextlib.AbstractContextManager[T, bool]]]
asyncutils.util.dualcontextmanager(
*,
use_existing_executor: bool,
create_executor: bool,
strict: Literal[True],
) collections.abc.Callable[[collections.abc.Callable[P, collections.abc.Iterable[T]]], collections.abc.Callable[P, contextlib.AbstractContextManager[T, bool]]]
asyncutils.util.dualcontextmanager(
*,
use_existing_executor: bool,
strict: Literal[False],
) collections.abc.Callable[[collections.abc.Callable[P, collections.abc.Iterable[T]]], collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]]
asyncutils.util.dualcontextmanager(
*,
create_executor: bool,
strict: Literal[False],
) collections.abc.Callable[[collections.abc.Callable[P, collections.abc.Iterable[T]]], collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]]
asyncutils.util.dualcontextmanager(
*,
use_existing_executor: bool,
create_executor: bool,
strict: Literal[False],
) collections.abc.Callable[[collections.abc.Callable[P, collections.abc.Iterable[T]]], collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]]
asyncutils.util.dualcontextmanager(*, strict: Literal[True]) asyncutils._internal.prots.StrictDualContextFactory
asyncutils.util.dualcontextmanager(
*,
strict: Literal[False],
) collections.abc.Callable[[collections.abc.Callable[P, asyncutils._internal.prots.SupportsIteration[T]]], collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]]
asyncutils.util.dualcontextmanager(
*,
strict: bool = ...,
) collections.abc.Callable[[collections.abc.Callable[P, asyncutils._internal.prots.SupportsIteration[T]]], collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]]
asyncutils.util.dualcontextmanager(
genf: collections.abc.Callable[P, collections.abc.Iterable[T]],
/,
*,
use_existing_executor: bool = ...,
create_executor: bool = ...,
strict: Literal[True],
) collections.abc.Callable[P, contextlib.AbstractContextManager[T, bool]]
asyncutils.util.dualcontextmanager(
genf: collections.abc.Callable[P, collections.abc.Iterable[T]],
/,
*,
use_existing_executor: bool = ...,
create_executor: bool = ...,
strict: Literal[False],
) collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]
asyncutils.util.dualcontextmanager(
genf: collections.abc.Callable[P, collections.abc.Iterable[T]],
/,
*,
use_existing_executor: bool = ...,
create_executor: bool = ...,
strict: bool = ...,
) collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]
asyncutils.util.dualcontextmanager(
agenf: collections.abc.Callable[P, collections.abc.AsyncIterable[T]],
/,
*,
strict: Literal[True],
) collections.abc.Callable[P, contextlib.AbstractAsyncContextManager[T, bool]]
asyncutils.util.dualcontextmanager(
agenf: collections.abc.Callable[P, collections.abc.AsyncIterable[T]],
/,
*,
strict: Literal[False],
) collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]
asyncutils.util.dualcontextmanager(
agenf: collections.abc.Callable[P, collections.abc.AsyncIterable[T]],
/,
*,
strict: bool = ...,
) collections.abc.Callable[P, asyncutils._internal.prots.DualContextManager[T]]

Convert a callable that returns an (async) iterable, usually an (async) generator function, over exactly one item, into a function returning a non-reusable sync- and async-compatible context manager. Essentially combines contextlib.contextmanager() and contextlib.asynccontextmanager() into one decorator.

asyncutils.util.evaluate_and_return[T, **P](
f: collections.abc.Callable[P, collections.abc.Awaitable[object]],
r: T,
/,
) collections.abc.Callable[P, types.CoroutineType[Any, Any, T]]

Return an async function with the same signature as f that awaits the result of f and returns r.

asyncutils.util.get_future[T](aw: collections.abc.Awaitable[T], loop: asyncio.AbstractEventLoop | None = ...) asyncio.Future[T]
Wrap an arbitrary awaitable aw in a task under loop, creating one and setting if required, and begin waiting on it.
Critical exceptions are wrapped in Critical.
This is as opposed to create_task(), which only takes coroutines.
async asyncutils.util.locked_lock[T: asyncutils._internal.prots.AsyncLockLike[Any]](*, lcls: type[T]) T
async asyncutils.util.locked_lock() asyncio.Lock

Return an already acquired lock of type lcls if passed and asyncio.Lock by default.

asyncutils.util.lockf[T, **P](
f: collections.abc.Callable[P, collections.abc.Awaitable[T]],
/,
lf: type[asyncutils._internal.prots.AsyncLockLike[Any]] = ...,
) collections.abc.Callable[P, types.CoroutineType[Any, Any, T]]

Apply a lock that implements the async lock interface, as constructed and returned by lf, to a function f that returns an awaitable, also converting it to an async function.

asyncutils.util.make_task_factory[T: asyncio.Task[Any]](tcls: type[T], eager: bool = ...) asyncutils._internal.prots.TaskFactory[T]

Return a task factory accepted by set_task_factory() that creates tasks of type tcls with the eager_start argument set to eager, its default value being MAKE_TASK_FACTORY_DEFAULT_EAGER.

asyncutils.util.new_eager_tasks[T](*aws: collections.abc.Awaitable[T]) types.GeneratorType[asyncio.Task[T]]

Yield eagerly started tasks wrapping the coroutines under the running loop (or a new one that is set as the current if required) in order.

async asyncutils.util.safe_cancel(fut: asyncio.Future[Any], /) None
Cancel a single future and wait for the cancellation to complete asynchronously.
The cancellation itself can be reliably cancelled, thus the name.

See also

safe_cancel_batch()

a more efficient way to cancel multiple futures at once, utilizing somewhat structured concurrency.

asyncutils.util.semaphore(bounded: Literal[False] = ..., workers: int = ...) asyncio.Semaphore
asyncutils.util.semaphore(bounded: Literal[True], workers: Literal[1]) asyncio.Lock
asyncutils.util.semaphore(bounded: Literal[True], workers: int = ...) asyncio.BoundedSemaphore

Return a (bounded) semaphore of value workers, defaulting to SEMAPHORE_DEFAULT_VALUE.

asyncutils.util.sync_await[T](
aw: collections.abc.Awaitable[T],
loop: asyncio.AbstractEventLoop | None = ...,
*,
never_block: bool = ...,
timeout: float | None = ...,
) T

Await the awaitable object aw under the given event loop loop with timeout timeout synchronously. If never_block=False is passed and the loop is not running, its run_until_complete() method may be called; otherwise, a pair of futures is created to coordinate the execution of the awaitable. It is preferred to use asyncio.run() to synchronously run one single top-level async function that awaits the necessary awaitables. Calling this function with the event loop running in the current thread will cause RuntimeError to be thrown.

asyncutils.util.to_async[T, **P](f: collections.abc.Callable[P, T], /) collections.abc.Callable[P, types.CoroutineType[Any, Any, T]]
Return the async version of the original function with all the attributes from its instance dictionary, which runs in an executor lazy initialized and shared by all to_async()-transformed callables.
If the argument was returned by to_sync(), a copy of the original async function is returned.

Warning

This function may create reference cycles. If memory is a concern, call gc.collect() regularly.

See also

AdvancedPool

an async-first thread pool executor-like class.

asyncutils.util.to_sync[T, **P](
f: collections.abc.Callable[P, collections.abc.Awaitable[T]],
/,
loop: asyncio.AbstractEventLoop | None = ...,
*,
timeout: float | None = ...,
) collections.abc.Callable[P, T]

Convert a function that returns an awaitable to an sync function with the same signature, using the event loop loop when required or creating when necessary.

asyncutils.util.to_sync_from_loop(loop: asyncio.AbstractEventLoop) asyncutils._internal.prots.ToSyncFromLoopRV

Return the partial of to_sync() under loop=loop.

asyncutils.util.transient_block[T, **P](
loop: asyncio.AbstractEventLoop,
f: collections.abc.Callable[P, T],
/,
*a: P,
**k: P,
) asyncio.Future[T]
asyncutils.util.transient_block(
loop: asyncio.AbstractEventLoop,
f: collections.abc.Callable[Ellipsis, T],
/,
*a: object,
_threadsafe_: Literal[True],
**k: object,
) asyncio.Future[T]
Run a sync function f, with the provided parameters passed straight through, in the event loop loop, and return an async future resolving to its result or exception.
This function avoids incurring the overhead of calling run_in_executor() by instead scheduling the function to run at the next iteration of the loop.
To avoid overhead, only use this on functions that return fast.
If _threadsafe_ is True, then the function is scheduled in a thread-safe way, so that this can be called from threads not owning the loop.
asyncutils.util.transient_block_from_loop(
loop: asyncio.AbstractEventLoop,
*,
threadsafe: bool = ...,
) asyncutils._internal.prots.TransientBlockFromLoopRV

Return the partial of transient_block() under the specified loop.

async asyncutils.util.wrap_in_coro[T](aw: collections.abc.Awaitable[T], /) T

Return a coroutine resolving to the result of the awaitable aw, such that it can be passed to asyncio.create_task().

asyncutils.util.anullcontext: asyncutils._internal.prots.NullContextType

An instance of an async context manager that does nothing.

asyncutils.util.ignore_cancellation: asyncutils.exceptions.IgnoreErrors

Context manager to ignore CancelledError.

asyncutils.version
A versioning scheme for asyncutils. Inspired by torch.torch_version, but with quite some differences.
asyncutils uses a subset of SemVer.
Classes

VersionDelta

VersionInfo

A class representing a version of asyncutils.

Functions

autogenerate_normalizers(→ bool)

Register normalizers for decimal.Decimal and fractions.Fraction. Return whether both normalizers were successfully registered, including re-registration of the same normalizer.

dispatch_normalizer(…)

Return the normalizer to be used for the object or type.

normalize(→ tuple[int, int, int])

normalize_allow_unimplemented(→ tuple[int, int, ...)

Like normalize(), but returns None if a normalizer is not found.

register_normalizer(…)

Register a custom normalizer for the object or type; return whether the normalizer was newly registered.

unregister_normalizer(…)

Unregister the normalizer for the object or type and return it if any.

Module Contents
class asyncutils.version.VersionDelta

Bases: NamedTuple

A named tuple-like class representing the difference between versions.
Not actually created by collections.namedtuple(), but implements its methods.
Accepted by the + or - operators.
__floor__() int

Return the major part of the delta.

__neg__() Self

Return the negative of the delta. Additions and subtractions taking the return value correspond to subtractions and additions taking the original delta respectively.

__replace__(*, major: int = ..., minor: int = ..., patch: int = ...) Self

Alias for _replace().

__trunc__() int

Identical to __floor__().

major: int = Ellipsis

The major part of the version.

minor: int = Ellipsis

The minor part of the version.

patch: int = Ellipsis

The patch part of the version.

class asyncutils.version.VersionInfo

Bases: str

A class representing a version of asyncutils.

Initialize self. See help(type(self)) for accurate signature.

__add__(n: int, /) Self
__add__(delta: VersionDelta, /) Self

Return this version incremented by n patches or the delta delta.

__ceil__() int

Return the major version, adding one if there is a minor or patch version.

__eq__(other: object, /) bool

Whether this version is the same as the other.

__float__() float

Assumes minor and patch are less than 100.

__floor__() int

Return the major version.

__format__(
format_spec: Literal['x', 'hex', 'o', 'oct', 'b', 'bin', 'd', 'dec', '0', 'major', 'maj', '1', 'minor', 'min', '2', 'patch', 's', 'short', 'l', 'long', 'a', 'ascii', 'c', 'chars', 't', 'tuple', 'h', 'hash', 'n', 'majmin'],
/,
) str

Format the version. See the return values below, using version 123.4.0 as example.

  • x, hex: '0x7b0400'

  • o, oct: '0o36602000'

  • b, bin: '0b11110110000010000000000'

  • d, dec: '8061952'

  • 0, major, maj: '123'

  • 1, minor, min: '4'

  • 2, patch: '0'

  • s, short: '123.4'

  • l, long: 'asyncutils version 123.4.0'

  • a, ascii: '{\x04\x00'

  • c, chars: '{\x04\x00'

  • t, tuple: '(123, 4, 0)'

  • h, hash: '116380397'

  • n, majmin: '123.4'

__ge__(other: object, /) bool

Whether this version succeeds or is equal to the other as a version.

__getitem__(idx: Literal[0, 1, 2], /) int
__getitem__(idx: asyncutils._internal.prots.ValidSlice, /) tuple[int, Ellipsis]

Return a property depending on the value of idx.

Slicing works as if the version object is a tuple of these three items, which is also accessible as parts.

__gt__(other: object, /) bool

Whether this version succeeds the other as a version.

__hash__() int
A perfect hash function for versions! May produce larger integers than __int__() in some cases, and may also produce negative integers.
Since hash() returns the output of __hash__() modulo 0x1FFFFFFFFFFFFFFF (largest Mersenne prime within 64 bits), the reasonable limit for versions that can be hashed and unhashed losslessly lies around VersionInfo(46340, 41707, 2147483645).
__index__() int

Identical to __int__().

__int__() int

Assuming minor and patch are less than 256, pack the parts into an integer, which can be larger than 24 bits to fit the major version. OverflowError is raised if not possible.

__iter__() collections.abc.Iterator[int]

Yield major, minor, patch sequentially.

__le__(other: object, /) bool

Whether this version precedes or is equal to the other as a version.

__len__() Literal[3]

len((major, minor, patch)) == 3.

__lt__(other: object, /) bool

Whether this version precedes the other as a version.

__ne__(other: object, /) bool

Whether this version is different than the other.

__radd__(n: int, /) Self
__radd__(delta: VersionDelta, /) Self

Return this version incremented by n patches or the delta delta.

__reduce__() tuple[type[Self], tuple[int, int, int]]

Support for pickling.

__replace__(major: int = ..., minor: int = ..., patch: int = ...) Self
__round__(ndigits: int, /) NoReturn
__round__(ndigits: Literal[1, 2, 3] | None = ..., /) Self

Support for rounding.

__setattr__(name: str, value: object, /) NoReturn

Disallow modifying attributes of the object.

__sub__(n: int, /) Self
__sub__(delta: VersionDelta, /) Self
__sub__(other: Self, /) VersionDelta

Return this version decremented by n patches or the delta delta, or the delta between self and other.

__trunc__() int

Identical to __floor__().

_replace(major: int = ..., minor: int = ..., patch: int = ...) Self

Satisfy the named tuple interface.

assert_valid() None

Signify an error if the user messed something up in this object, likely intentionally.

change_sep(sep: str) str

Return this version as a string with the specified separator instead of a dot between parts.

compatible(other: Self, /, maj_tol: int | None = ..., min_tol: int | None = ...) bool

Whether this version is compatible with the other, given the major and minor tolerances.

classmethod from_hash(hashed: int) Self

Reconstruct the version from its hash.

classmethod from_rep(rep: str) Self

Parse the string representation of a version to get the version back.

classmethod get_current_version() Self

Return the current version number of asyncutils; equivalent to asyncutils.__version__.

is_current_version() bool

Whether this version is the same as the current version of asyncutils.

replace_parts(*, major: int = ..., minor: int = ..., patch: int = ...) Self

Another instance of this class with the specified parts.

shelve(path: asyncutils._internal.prots.Openable, /, key: int = ...) None

Store this version into the specified path, non-cryptographically transforming the bytes with key, which can be any integer.

to_complex() complex

Loses the patch version. Since this class is a str subclass, an implementation of __complex__() will not be recognized.

classmethod unshelve(path: asyncutils._internal.prots.Openable, /, key: int = ...) Self

Recover a stored version from path. A wrong key would usually raise an error, and even if it doesn’t, the version would be wrong.

DEFAULT_KEY: Final[int]

The default value of the shelving and unshelving key.

property major: int

The major part of the version.

property minor: int

The minor part of the version.

property next_major: Self

The major version following this version, with minor and patch 0.

property next_minor: Self

The minor version following this version, with a patch of 0.

property next_patch: Self

The patch version following this version.

property parts: tuple[int, int, int]

The tuple (major, minor, patch).

property patch: int

The patch part of the version.

property representation: str

String representation of the version for pretty printing, used by asyncutils -v.

asyncutils.version.autogenerate_normalizers() bool

Register normalizers for decimal.Decimal and fractions.Fraction. Return whether both normalizers were successfully registered, including re-registration of the same normalizer.

asyncutils.version.dispatch_normalizer[T](o: type[T], /) collections.abc.Callable[[T], collections.abc.Iterable[int]] | None
asyncutils.version.dispatch_normalizer(o: T, /) collections.abc.Callable[[T], collections.abc.Iterable[int]] | None

Return the normalizer to be used for the object or type.

asyncutils.version.normalize(o: object, /) tuple[int, int, int]
Return a tuple of three integers (major, minor, patch) from the information provided by the object as extracted by registered normalizers.
A normalizer can return None for an unnormalizable object, in which case the comparison operators against instances of VersionInfo will delegate to the object itself.
If the normalizer raises an exception or returns a non-iterable, it is removed and the error is propagated.

Note

Normalization logic is hardcoded for exact instances of str, complex, int, and float. This takes precedence over any registered normalizers, but those can still be accessed with dispatch_normalizer().

Note

For iterables, the default behaviour is to take the first three items and pad zeros behind if necessary.

asyncutils.version.normalize_allow_unimplemented(o: object, /) tuple[int, int, int] | None

Like normalize(), but returns None if a normalizer is not found.

asyncutils.version.register_normalizer[T](o: type[T], f: collections.abc.Callable[[T], collections.abc.Iterable[int]], /) bool
asyncutils.version.register_normalizer(o: T, f: collections.abc.Callable[[T], collections.abc.Iterable[int]], /) bool

Register a custom normalizer for the object or type; return whether the normalizer was newly registered.

asyncutils.version.unregister_normalizer[T](o: type[T], /) collections.abc.Callable[[T], collections.abc.Iterable[int]] | None
asyncutils.version.unregister_normalizer(o: T, /) collections.abc.Callable[[T], collections.abc.Iterable[int]] | None

Unregister the normalizer for the object or type and return it if any.

Glossary

extra

A name corresponding to a set of optional dependencies, supported by most package managers (pip, pipx, conda and uv). This module has no runtime dependencies outside of the standard library save for the config file parsers, and all the extras are for development only.

submodule

A module that is part of a library or package that is not the main module/entry point. See Submodules.

subpackage

A directory within a package containing submodules, along with an __init__.py file.

entry point

A function serving as the main interface for a module or package, allowing it to be run as a command-line tool or imported as a library.

Contributing

When contributing to this repository, please first discuss the change you wish to make via issue, email, or any other method with the owners of this repository before making a change.

Please note we have a code of conduct and AI Usage Policy, which you should follow in all your interactions with the project.

Pull Request Process

  1. Fill in the pull request template, following it as faithfully as you can.

  2. If applicable, update the README with details of changes to the interface, including new environment variables and useful file locations where appropriate. There should already be a section for each of the above cases. Do not add a new section without another issue.

  3. Once you have the sign-off of one other developer, you may either merge the PR yourself if you have permission, or ask the reviewer to do so on your behalf otherwise.

Notes

Do not abuse your write access to the repository to, for example, create a fake or unprompted release, or it will be unequivocally revoked. Besides, merging without a review is prohibited for any developer other than the owner.

AI Usage Policy

In short, please keep these two principles in mind when you contribute:

[!IMPORTANT]

  1. Never let an LLM speak for you.

  2. Never let an LLM think for you.

This project does not accept fully AI-generated pull requests. AI tools may be used only for assistance (e.g. understanding existing code, writing out well-known algorithms). You must understand and take responsibility for every change you submit. We reserve the right to reject pull requests that contain little or no genuine contribution from the contributor (with regards to code as well as the thought behind changes).

Our Rule

All contributions must come from humans who understand and can take full responsibility for their code.

Large language models (LLMs) make mistakes and cannot be held accountable for their outputs. This is why we require human understanding and ownership of all submitted work.

[!WARNING] Maintainers will close PRs that appear to be fully or largely AI-generated.

Getting Help

Asking questions can indeed feel intimidating. You might worry about looking inexperienced or bothering maintainers with “basic” questions. AI tools can feel like a safer and less judgemental first step. However, LLMs often provide incorrect or incomplete answers, and they may create a false sense of understanding.

If you do end up using AI tools, we ask that you only do so in an assistive (like a reference or tutor) and not generative (having the tool write code for you) manner.

Guidelines for Using AI Tools

  1. Understand fully: You must be able to explain every line of code you submit

  2. Test thoroughly: Review and test all code before submission

  3. Take responsibility: You are responsible for bugs, issues, or problems with your contribution

  4. Disclose usage: Note which AI tools you used in your PR description

  5. Follow guidelines: Comply with all rules in the contributing guide

Example disclosure

I used Claude to help debug a test failure. I reviewed the suggested fix, tested it locally, and verified it solves the issue without side effects.

I used ChatGPT to help me understand an error message and suggest debugging steps. I implemented the fix myself after verifying it.

What AI tools can do (assistive use)

  • Explain concepts or existing code

  • Suggest debugging approaches

  • Help you understand error messages

  • Run tests and analyze results

  • Review your code for potential issues

  • Guide you through the contribution process

What AI tools cannot do (generative use)

  • Write entire PRs

  • Write replies to PR review comments

  • Submit code the contributor doesn’t understand

  • Generate documentation or comments without contributor’s review

  • Automate the submission of code changes

Why do we have this policy?

AI-based coding assistants are increasingly enabled by default at every step of the contribution process, and new contributors are bound to encounter them and use them in good faith.

While these tools can help newcomers navigate the codebase, they often generate unhelpful submissions that appear legitimate, and require considerable time for maintainers to reject.

There are also ethical and legal considerations around authorship, licensing, and environmental impact.

We believe that learning to code and contributing to open source are deeply human endeavours that requires curiosity, slowness, and community.

Questions?

If you’re unsure whether your use of AI tools complies with this policy, ask in the discussions or in the relevant issue or PR thread.

Disclosure

This document is based on its analogue from JabRef.

Development Chores

This file aims to detail guidelines for some monotonous tasks contributors to this library may need to complete in different recurring scenarios.

Preliminaries

You are recommended to install an IDE plugin to support .editorconfig and use a grammar and spelling checker. Regarding .markdownlint.json, even though there is no longer a pre-commit or workflow step requiring it, it contains the most basic ignores suitable for this project’s files and should be respected. You should run the linter locally to check for markdown stylistic issues. Also ensure you have pre-commit installed from pip and the hooks activated using pre-commit install, you have cspell and @cspell/cspell-tools installed (e.g. from npm), and that you are comfortable with having uv installed on your system.

Adding words to the incorrect spelling whitelist

Edit assets/words.txt and check for regressions with make spellcheck. The file is kept sorted by a pre-commit hook for aesthetic reasons.

Bumping the version

Using something like uv version --bump patch to increment the patch version may not work because the version as a string is hardcoded into certain locations, some of which are to be left untouched. Instead, follow these steps:

  1. Do a per-file find-and-replace in your preferred IDE after inspecting each instance to avoid unintended changes. __version__ is already instantiated from a string to streamline this step.

  2. In pyproject.toml, there may be optional dependencies whose version coincides with the project’s, so take care not to modify those as well.

  3. Also exclude the CHANGELOG.md at the project root from the replace operation.

  4. A core developer of this project will help you create a GitHub release with default release notes, since you are not allowed to do so yourself. (Core devs, this is make release.) This will automatically trigger a stable Read the Docs build, a push to PyPI and cause a conda-forge bot automerge.

  5. If you include your desired remarks in the PR under a “Release Notes” section, those will be used as the release notes instead after the developer tries their best to correct grammatical or spelling mistakes.

Note

There is no lower bound on the number of patches per minor, though because support for packing versions into integers in a specific format must be supported, and there is concern of code churn or low-quality changes, the upper bound is 256, i.e. the numbers from 0 to 255. The same applies for minor releases per major, but we aim to drop majors every year and minors per month, so this should be a non-issue.

Implementing a new utility

Add proper stubs for it in the .pyi file and include it in the appropriate <submodule>_all declaration in asyncutils/_internal/submodules.py. Also add tests such that the coverage does not dip past a certain extent.

Adding a new submodule

  1. Search for ‘rwlocks’ (without the quotes) across all files in the repository, excluding asyncutils/rwlocks.py, asyncutils/_internal/types.pyi and this file. This should reveal all the locations where submodule names are referenced. Still check each one to see if it is a correct place.

  2. Insert the new submodule name as a string in those occurrences, maintaining alphabetical order where applicable.

  3. Bear in mind that the submodule name should not have more than one word, should not contain underscores or uppercase letters, and a stub should be created for it that contributors should update in parallel. The stubtest tool from mypy will not work because we use ty ignores that mypy doesn’t recognize, causing stubtest to report something along the lines of “Not checking due to mypy build errors”.

  4. Add a test file for the new submodule importing all names from the submodule.

Adding a new configuration option

This will not usually be done by a contributor, only a collaborator, because there should be evidence that the change is imperative or desirable in a dedicated GitHub discussions thread. Stack Overflow is only for general questions; you should really not tag asyncutils there.

After reviewing the pitch, the collaborator will step in and make necessary changes to the argument parser, documentation and internal machinery.

For collaborators and those interested, this is the general procedure:

  1. Edit the setup of the argument parser and the dictionary of defaults N in _internal/unparsed.py.

  2. Edit format.json5 by adding the key in the same order as the new help from the parser appears and a comment describing what it does, and take note of the line numbers where the pairs corresponding to logging configuration are shifted to.

  3. If the value of the configuration option is to be accessible by users at runtime, it should be in the form of a symbol in config.

  4. Update config.pyi, noting the line numbers at which the logging-related declarations appear.

  5. Edit the definition of json_to_argv() and update the test suite to account for that, preserving round-trip conversion as promised.

  6. Update the literalinclude’s in logging.rst with the line numbers jotted down from steps 2 and 4.

  7. Execute the platform-suitable genhelp script without committing the outputs. This serves as a sanity check.

Adding a new contextual constant

The name of the constant should be of the form UTILITYNAME_OPTIONALMETHODNAME_DEFAULT_ARGNAMEINCAPS if it acts as a dynamic default value, the most common case by far. Note the uppercase, underscores and rigid format.

After verifying the integrity of the field name according to this metric, navigate to the following locations relative to the project root and complete the following:

  • asyncutils/format.json5

    Find the submodule and add in part of the option name in the object under the appropriate pattern. If this causes there to be more than one option for a utility with no dedicated mapping having it as key, create one and merge the other in. If these guidelines sound vague, surrounding keys will help you. Bear in mind that because of organizational, readability, maintainability and consistency standards, the options should be in the same order as those in context.pyi, as elaborated on below.

    Caution

    The option name should be lowercase, as opposed to being fully capitalized like how you are recommended to access it.

    Attention

    Also remember to update the line numbers in the literalinclude directive referring to format.json5 in logging.rst.

  • asyncutils/context.pyi

    Be sure to update the contextual constant count:

    Keep alphabetical order within the submodule concerned, with submodules ordered alphabetically as well.

  • asyncutils/_internal/unparsed.py

    There should be a massive dictionary assigned to the name C that contains the option names mapped to their factory defaults on line 5. Edit it accordingly.

Updating config.pyi

Special care must be taken, since the Logging page depends on the exact line numbers at which specific symbols are declared here in the form of a literalinclude. The same applies for format.json5. Take a look at the current state of the site, and hopefully you can determine what the new line numbers should be accordingly.

Adding a documentation page

  1. Choose a format: .md or .rst. Though .md is easier to write, one may want .rst for its rich directive support that integrates seamlessly with Sphinx and allows for smoother redirection, though the MyST parser is improving to accommodate these.

  2. Choose a location depending on how visible you wish the page to be: docs/source or the project root.

  3. If the page is of paramount importance even to end users or people doing a read-through of the project, expand the README with a new section containing a summary and linking to the page on the bottom.

  4. Update the relevant table of contents tree (toctree) in docs/source/index.rst. Do not move documents across the four different trees.

  5. If copying from the root to the Read the Docs page is required during build, so that users can see it in both places, add an entry to the mapping representing sources and respective targets for copy statements inlined in .readthedocs.yaml, maintaining alphabetical order.

Note

autoapi_keep_files is set to True in conf.py only to allow local incremental builds. This is why the docs/source/api directory is in .gitignore, and you should not commit it.

Changing help messages for command-line arguments

Remember not to indent the help strings when using multiline strings; keep them at the left margin such that they display correctly.

If you want to preview the changes to the argument parser help in the form of an HTML page, run ./scripts/unix/genhelp.sh on Unix or .\scripts\win\genhelp.ps1 on Windows before running the sphinx-build command. Do not, however, commit the resultant file.

Modifying the Makefile

Remember to sync up the Makefile with make.bat in the same directory, and vice versa. If you wish to remove a target, it must have exceeded a previously declared deprecation period, and been moved into a special section with a “Deprecated targets” header in the make help output.

If you want to preview the changes to the help message in the form of the eventually created page, run ./scripts/unix/genmakefileusage.sh on Unix or .\scripts\win\genmakefileusage.ps1 on Windows before running sphinx-build. Do not, however, commit the resultant file.

Adding tests

Make sure the name of the test function is prefixed with “test_” such that pytest correctly discovers it. Run pytest, selecting only that test, to verify the test is written correctly and your implementation is resilient against edge cases.

Tip

If you are puzzled as to how to write tests for your feature, you may simply try it out in the console and check its behaviour against your expectations. As long as you include the statements you entered in the console in your issue or PR description, the maintainer making the merge commit can write the tests for you.

See also

This basic pytest how-to

assert statement usage and other fundamental guidelines, for those more used to other frameworks like unittest.

Before committing, run the whole test suite by entering the following command at the project root to check for regressions and update the relevant static badges in the readme:

make gen-badges

If the tests are failing, do not commit the badges, since reviewers would assume your PR is ready for merging when you do so, and may close the PR just because they don’t appear with a passing status.

Note

The above snippet requires the pytest-local-badge plugin, which should come packaged with the tests dependency group.

The test ought to go in the test source file corresponding to the submodule from which the feature can be publicly imported, even if its implementation is spread across files, with the exceptions of the base and iterclasses submodules, whose tests I find inseparable with the logic for tests for iters, compelling me to put them into tests/test_iters.py together.

Using the Makefile

make.bat on Windows, or Makefile on *nix, is often a handy companion in development. It makes development less dry, repetitive and error-prone, and the process as a whole more smooth-sailing. Tasks are effectively automated using the make <target> syntax.

This is partly also to compensate for the lack of a setup.py after adaptation of the standardized pyproject.toml; see PEP 621 and the official PyPA guide for more. Note that the Makefile is not intended to be used by end users, but rather by developers, and it obviously requires GNU Make.

If you are in PowerShell, make will not work directly and you must run .\make or .\make.bat instead, which is more verbose; thus, you are strongly advised to develop in cmd.exe, the traditional command prompt.

Below is the Makefile help as of asyncutils v1.1.0:

Available targets:
 audit-deps     - Run a security audit on all (optional) dependencies using uv
 build-docs     - Build a preview of the documentation in docs/build/html, exiting with a non-zero status on any warning
 changelog      - Generate a compact changelog from Git history and print it in the terminal with colour
 clean          - Clean development artifacts and caches, including the __pycache__, build and dist directories, generated files, and coverage results
 gen-badges     - Run the test suite twice, exiting on any failure; generate static badges on success
 gen-baseline   - Regenerate the detect-secrets baseline at the project root
 help           - Show this help message
 install        - Install the package in editable mode with development dependencies; assumes a virtual environment is present
 install-silent - Install without output
 pre-commit     - Run pre-commit hooks on all files, assuming the executable pre-commit on PATH points to pre-commit
 release        - Call the GitHub CLI (gh) to make an release interactively
 ruff           - Run the ruff linter
 spellcheck     - Run CSpell
 test           - Run tests, allowing up to AUTILSTESTMAXFAIL failures (default 3) since any more would likely mean an obvious error
 type-check     - Run ty for type checking
 venv           - Create a virtual environment using uv
 watch          - Watch for changes and run tests automatically using pytest-watch, assuming it is installed
Note: Some targets will automatically install or update the uv package manager. Targets may be added on popular demand.

Note

Generated by scripts/unix/genmakefileusage.sh in Read the Docs latest build at 2026-07-11 10:54:00 UTC.

Benchmarks

“Statistics are like bikinis. What they reveal is suggestive, but what they conceal is vital.”

—Aaron Levenstein, 1951

Note

The above quote is not to downplay the importance of this document, but the performance of async code depends heavily on the event loop implementation, which is not well captured by this data because only import time is counted.

When used as a REPL (Read-Eval-Print Loop), this module starts slow since it builds on the standard library asyncio, which loads all its submodules on import, and the event loop is quite difficult to implement. This is understandable but suboptimal. On the contrary, we focus on simplifying boilerplate-heavy code and integrating and combining existing patterns seamlessly with a set of core utilities, so asyncutils is not at all heavy in terms of import time. In addition, you only pay for what you use; the parts of the code you don’t call are not executed until you request them to be, thanks to cleanly separated submodules with somewhat simplistic dependency graphs. This module is overall fast and light because of its design goals and philosophy.

The figures below are obtained by running each of the following sequentially with no warmup elevenfold in a fresh console session and discarding the first run (warmup):

Environment

  • python -VV gives: Python 3.14.6 (tags/v3.14.6:c63aec6, Jun 10 2026, 10:26:10) [MSC v.1944 64 bit (AMD64)]

  • python -m platform gives: Windows-11-10.0.26200-SP0

  • __pycache__ directories are persisted across runs

It would be very nice if somebody could do the benchmarks on Ubuntu or other platforms and add a new section with the same structure detailing the results, since asyncio works drastically different on Windows than other systems.

Note

The user and sys measurements below have a granularity of 15 ms.

Baseline: asyncio

python -SIqX importtime -c "import asyncio"

Cumulative import time of asyncio: 122.60 ± 10.14 ms; max 138.83 ms, min 103.49 ms; n = 10

time printf "raise SystemExit\n" | python -SIqm asyncio 2>/dev/null

Time taken to start and immediately exit the asyncio console:

  • real: 500.7 ± 14.5 ms; max 520 ms, min 474 ms

  • user: 42.0 ± 28.1 ms; max 105 ms, min 15 ms

  • sys: 67.5 ± 19.1 ms; max 90 ms, min 30 ms

n = 10

Note

This includes Python startup time and immense I/O and process overhead with piping.

Note

The time command is not really a benchmarking tool, so these are rounded to 0.1 ms. It is also run in Git Bash on a slow computer. This must be improved on in the future.

asyncutils

python -SIqX importtime -c "import asyncutils"

Cumulative import time of asyncutils: 147.34 ± 7.53 ms; max 156.40 ms, min 131.94 ms; n = 10

Note

The figures below are relative to the time when asyncutils/__init__.py is executed, and may not reflect the actual time taken, because Python is not free to boot up itself, having to perform various initialization tasks.

python -SIqm asyncutils -dl

Time taken to start the console, which includes importing asyncio: 99.89 ± 6.19 ms; max 110.25 ms, min 91.97 ms, n = 10

python -SIqm asyncutils -dpl

Time taken to import asyncio along with all 31 ordinary submodules: 196.96 ± 18.30 ms; max 225.08 ms, min 172.51 ms, n = 10

Note

Up to 10 required internal submodules are also fetched.

time printf "raise SystemExit\n" | asyncutils 2>/dev/null

Time taken to start and immediately exit the asyncutils console, timed like the asyncio console:

  • real: 380.8 ± 22.7 ms; max 412 ms, min 350 ms

  • user: 25.5 ± 17.4 ms; max 45 ms, min 0 ms

  • sys: 37.5 ± 17.7 ms; max 60 ms, min 0 ms

n = 10

time printf "load_all()\nraise SystemExit\n" | asyncutils 2>/dev/null

The above including all submodules:

  • real: 485.3 ± 12.2 ms; max 506 ms, min 459 ms

  • user: 19.5 ± 10.1 ms; max 30 ms, min 0 ms

  • sys: 55.5 ± 17.4 ms; max 90 ms, min 30 ms

n = 10

Note

asyncio is still loaded early such that attribute accesses later on would not randomly take more than 100 ms, and you logically wouldn’t use this module without an async entry point, such that asyncio and its event loop are crucial and unavoidable.

Compatibility

Python versions

We strive to have released versions support all Python versions actively maintained at the time of release, but due to logistical constraints and major syntactical reworks in 3.12, we will not support Python 3.11 or below. However, the weaker promise to support all actively maintained versions of Python will be upheld; that is, users need never worry about support for the newest version and the one before it. Also, this codebase is quite future-proof, integrating modern features such as lazy imports non-intrusively and using the newest compatible syntax.

Our compatibility layer, currently backports the shutdown() method of asyncio.Queue and the Placeholder support in functools.partial(). The latter performs slower than its C-accelerated counterpart.

See PEP 602 for a detailed explanation of the Python release cycle, and the status of Python versions.

Support matrix

asyncutils version

CPython version

6.0 - 6.11

3.14+

5.0 - 5.7

3.13+

1.0.0 - 4.7

3.12+

0.8.18 - 0.9.16 (EOL)

3.12+

0.8.0 - 0.8.17 (EOL)

3.14+

Code of Conduct

Our Pledge

In the interest of fostering an open and welcoming environment, we as contributors and maintainers pledge to making participation in our project and our community a harassment-free experience for everyone, regardless of age, body size, disability, ethnicity, gender identity and expression, level of experience, nationality, personal appearance, race, religion, or sexual identity and orientation.

Our Standards

Examples of behaviour that contributes to creating a positive environment include:

  • Using welcoming and inclusive language

  • Being respectful of differing viewpoints and experiences

  • Gracefully accepting constructive criticism

  • Focusing on what is best for the community

  • Showing empathy towards other community members

Examples of unacceptable behaviour by participants include:

  • The use of sexualized language or imagery

  • Unwelcome sexual attention or advances

  • Trolling, insulting/derogatory comments, personal or political attacks

  • Public or private harassment

  • Publishing others’ private information, such as a physical or electronic address, without explicit permission

  • Other conduct which could reasonably be considered inappropriate in a professional setting

Our Responsibilities

Project maintainers are responsible for clarifying the standards of acceptable behaviour and are expected to take appropriate and fair corrective action in response to any instances of unacceptable behaviour.

Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviours that they deem inappropriate, threatening, offensive, or harmful.

Scope

This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community.

Examples of representing a project or community include using an official project e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event.

Representation of a project may be further defined and clarified by project maintainers.

Enforcement

Instances of abusive, harassing, or otherwise unacceptable behaviour may be reported by emailing me. All complaints will be reviewed and investigated and will result in a response that is deemed necessary and appropriate to the circumstances. The project team is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately.

Project maintainers who do not follow or enforce the Code of Conduct in good faith may face temporary or permanent repercussions as determined by other members of the project’s leadership.

Attribution

This Code of Conduct is adapted from the Contributor Covenant, version 3.0, available on their official page.

Support Guidelines

Thank you for using asyncutils! This document outlines how to get help with this project.

Before jumping to seek support, do skim through the readme.

Bug Reports

If you’ve found a bug, please:

  1. Check if it’s already reported in Issues

  2. If so, participate meaningfully there; create a new issue otherwise

  3. Refer and adhere to the issue template chosen, or risk your issue being closed without going through actual review

Feature Requests

Have an idea? We’d love to hear it!

  • Search existing issues to avoid duplicates

  • Explain the use case and expected behaviour

  • Include examples unless you think the idea is straightforward enough

Questions

Community Support

Quick Questions

For quick questions, consider:

  • Checking existing issues/discussions

  • Reading the FAQ section below

  • Asking in community channels

Security Issues

Never report security vulnerabilities publicly.

See the security policy for details.

Common Issues & Solutions

Installation Problems

Update your package installer, then try the following fixes:

uv pip install -U py-asyncutils # Upgrade
uv pip check # Check for dependency shenanigans
uv pip tree # Pretty print the pip packages dependency tree
uv pip tree --package py-asyncutils # Show only the dependents and dependencies of this package
uv pip uninstall py-asyncutils && uv pip install py-asyncutils # Clean install

Other (slower) package managers:

# pip
pip install -U pipdeptree && pipdeptree # Quite a bit more clutter than uv pip tree, showing a single package repeatedly
pipdeptree --packages py-asyncutils # Only this package as above

pip install -U pipx && pipx ensurepath # pipx, installed with pip
conda update py-asyncutils # conda

Import Errors

Check if asyncutils is installed:

pip list | grep py-asyncutils
# or
pip show py-asyncutils
# uv
uv pip show py-asyncutils

If the package is not working with python, perform the steps below:

# Check sys.path
python3 -c "print(*__import__('sys').path, sep='\n')"
# Check for package naming conflicts; following snippet should print altlocks, base, buckets, channels, cli, compete, config, console
# constants, context, events, exceptions, ... separated by newlines
python3 -c "print(*__import__('asyncutils').__all__, sep='\n')"
# If not loading site, repeat the above steps w/ python3 -Sc

Response Times

As fast as I can; that is:

  • Bug reports: 3 days

  • Feature requests: Reviewed biweekly

  • Security issues: 1 day

  • General questions: Community-driven

I will try to make a post on the discussions page (e.g. hiatus announcement) and set my status to ‘On vacation’ or similar in case of inactivity such that I cannot fulfil these promises or meet other deadlines I set myself.

Remarks

Don’t:

  • Bump issues with +1 or “me too”

  • Email maintainers unless urgent

  • Ask about ETA of features/fixes

  • Post API keys or passwords

Instead:

  • React to issues

  • Open discussions or issues, or a pull request if the problem is easily fixable

  • Be patient

Once again, thank you for supporting this small project. Happy programming!

Security Policy

Supported Versions

Version

Supported

1.0.x

Yes

0.9.x

No

0.8.x

No

Reporting a Vulnerability

It is thought to be highly unlikely that there will be any security vulnerabilities will emerge in the near future, since the nature of this project means it should not see much applications in security-sensitive fields, but this is still included for compliance with OpenSSF Best Practices standards. Please report as follows:

  • GitHub-native method

    Navigate to the security tab, then click on “Report a vulnerability” in the upper right corner. Comprehensive guidelines should be shown.

  • Via email

    Send me an email.

    If possible, encrypt your message with PGP. The fingerprint is 836B3C7AA3DAC6337F61CD2D2A5943B64B0994DE, and the public key is shown below.

    Always check the key against the fingerprint first in case the former was compromised.

-----BEGIN PGP PUBLIC KEY BLOCK-----

mQINBGo7HtgBEADPt87nahP4eGvqBIveMF/MHgNE5s6KCi3MI78TzT5DWcHdc/vY
DZM4ldOlD2Y5O50pnpEn6AcwchQCJ8rQI1erhsqIAyCh/t6btQThhzgYiLmTu6PX
cP+SMCLh9DpONgP6et/vzyOXwYopfp3StVg6aWFZqC5v5kFA+NiJsaMsnHx8B423
DhC4mD2rOpllNlz6h/7B2kaz5PL0jD57p74IEBHV0Bmpbt+DA+dyGsaZDLx7bDEs
Ujexy8J75DVBB8NiDhWEqmLAk64kAYfoHJUScgFfT6ShTngRUQXpif3eo/kL4wgP
K4ZTQeaOQ5dXNjil+zSdRWCE7SAuQbexRSrX0YO1x/W9xG8KGcWhQfSQOXHULVoq
Cl/YRexpBsfnExvcQd5sleTM0EjKXImekvpku+V7uTmpMnYWLEN3ktfX602ExTbP
ymW4/Bx0lzqVLEHg6B5IgXY9VL+10TsEwNq/29Zes5FZQqPq2rgIFWEK6AOdyi2X
fT5QpHEvC15neK336nveGAyYtTRTOGjoVV3Vlf6O6lCsP50fm63qLkNB1THB0L8q
CeNiEudFG2A9mZVL8lhfK1R89hAYqROU1IWUeu9TlEBpRl/C50llxhJ1eEuUTy8p
Wtb9t78tXr1/PL1ijrgcfnMio/39Y7C6cZzhNMX+Ck+jiAShmHmHlbyPCQARAQAB
tCZKb25hdGhhbiBEdW5nIDxqb25hdGhhbmR1bmdAeWFob28uY29tPokCbQQTAQgA
VxYhBAt1z1esidoZQwrzlVNvZeUL5LIzBQJqOx7YGxSAAAAAAAQADm1hbnUyLDIu
NSsxLjExLDIsMQIbAwULCQgHAgIiAgYVCgkICwIEFgIDAQIeBwIXgAAKCRBTb2Xl
C+SyMxI4EACSQhTyfnLmn1AfEIhW3wmLEkBnact1drTfWbp2AXyj+R9ESltLQiDc
PFCc6ARQhesyDaa5dR5mnNiAdCnLTYksQG8KYkrk9E2Xx2N9lfMPGWy2EP2z/PSE
DMYYwZ7fqYZxnsZHyRHuweCasKaawa21DvAbtHBkN1rYIOY3r69xacno3n1w/gC6
IXlAC0V56inLjSFqZqTp6W72CTHGD6/Zt2hFw9CSIgzrbbJTxI0tyrqv2IniV0lL
JdpcpauxgNmmJpnLcWZPVxh6/nJyYTae0OA5U+d2uQerpmqzyZZTrlbLs1BjSEgH
uzgjvVSRDTcqta8HZWBy55ktlPQeH5AMSrLbM1C28gia5KoT/i6pk3lhzK1bK8/k
Jxd8mQSxOrdCNyvW12aTL9ChXgsoiJQrb2Gc8MxPLaf+3PxBYFrcsQqpxr6ki/m5
Bv6fUkYqHsgv4qkC/67RnA1+0xfseo/7pcxbVIdJ8aPtrBvcTxAxDslwSjxVObQZ
C/8vD1Xa/SpR928dpIuzf1iHtClz/LO9zvicyEkbLwu4Q2Vl5IBpu71t9HhfkYoQ
fSFULeuo3rEHqxJ66bPA0csuW7i51/PTCN4CKcVYbz1ZWLK+lsLdzsJgUzRdEbol
f0OTvsK53SazeuBS4z7Oq7NQfm1306SDJjwJgJdglxVhws76sFqdMbkCDQRqOx7Y
ARAA7YGEOVFkiKZJ986zW6xhPGHSbYYjPbsiDUKaRFnqNm3bFXm2soFrnXwogSl8
m4XVnIJWwVvvh6OlNCJojAuwQ4qODIA3CJyRdwyTP1WsfdWkEvXklv6HwLkGiJs9
tnFokXeIoa9igQv44g01QTMX9sYPJBx5NJOCehoGg2Yucunkutcy0xSCjCYSHH18
QTHAuzUBTTVHbVri3j4LI61RjXP4DeUgDmGGBHQIqDgcg53jEMt+vJLvbZomifBr
oR+6uOcg/gS1IaK7c3FYR9k+YUsOS3cA+yRxNNpP0jAs2xKSc6iQBhKNyS5HmK8o
eCQbHql/Y4BlfktLoTK+Gz2TzAuQkW2kNMVbv7zzbL9oJwPvtyfrslCPAabDlXiA
GVL+B/C3BKBymiIh85daLY/8Z8WWDDU5ZGdkAuDE3QlzmbkCLyoZNQpN+jlXnjlj
butYkgjmlZED9gxFuOYGMqgANax+28yXf9jEujFV2jWA0wvfJQ3qzpUfRZnhDMHd
o+QOyJyTj+nhzVZ6DWoKsw+VNLzXr5IQHYkKcFBOeKgJ0sgW5SL50avqkv5v6yqH
Pl14cNjizOppu7LM2Ma+seYawEg3elMmhyKcwaYpYZIDVnYDiWC0L6Fr6cfbWsqS
pcmFjfqyure/9Yd7iZDzF59i+bFI6A7+8r4oWiePeNEIh0EAEQEAAYkCUgQYAQgA
PBYhBAt1z1esidoZQwrzlVNvZeUL5LIzBQJqOx7YGxSAAAAAAAQADm1hbnUyLDIu
NSsxLjExLDIsMQIbDAAKCRBTb2XlC+SyM+DbEADNlMcIGWxpTwcFqSp0We1R9+2n
8bhR3ra1yt/EU2il+ABQfMDom6yLME6xkM4d0f6QRR3JrDDFUqK5waCbKzHmIvCQ
sIiEPaJ8KO8KHwbbgIQc34AMSSsEpc2b3Tw5lhK7IUSFuo5nUYVY8MBU4FEPvLj+
h2xXxaPzhcCAIvFdXdFJfay06TePZMPyltWYfsjqS3PlKWzI942AqBCIcfoGrHzw
sr1Q+xMP674ryqBtjncB1XVS5Vg/MliNv4Upy39r91Mb1BkAC0Y19r8zpEeqyxMX
4TNAKp69dMgac83WkcER7M+p6OsR0jQlCvif5uYIGVKpWrTPErFaTQR8cuc9uNFr
tTSkqPV3UeGIVdWiRfrSG8KYtrG7XKG6ctoCKn1tGxtAWvw5pPStr0qk7TP7XvC/
uaGkd6NWimg77Xe9U2KHDt5WEKDrz1O2+G9b3mRkQGbadceia1vFFEerfGEwoCJx
Z7QZ+qySSyviv/+0NiFGEnCsqjzaBD3iDKcdrGea6fV3C0iGSX9aFv0z4hXittHh
61PimTjhoLN83htu0sOh2520dgn8gA9qlsK0sIfTexVlqzpfiFIaa7BZTBznY0ag
g+2f1A/STRWEVkqovXENDL5VqOYgjekMkB6FToKvjuSz/wxBFddb91Ach/7hhxsq
rWla7H0vCY+jhY7QLw==
=MQQl
-----END PGP PUBLIC KEY BLOCK-----

Thank you for your report in this unfortunate scenario. If you wish not to be acknowledged, please specify so in the email.

Please note that reporting such potential exploits, if they are to emerge, via public channels such as the issues tab, is a sure-fire way to notify the attackers (if any), who may then adjust their strategy. Therefore, you should ensure the communication method chosen is secure according to the directions above.

Changelog

All notable changes to this project are and will be documented in this file.

This project uses Semantic Versioning when I feel like it.

Summary

Tests

58% coverage, 87 tests

Docs

96% complete

Versions

[1.0]

Breaking changes:

  • Declared end of life for all beta versions.

  • Included all the symbols listed in the previous section in the public API.

[1.1.0] - 2026-07-11; newest

Semantic versioning be damned! No one uses this project anyway.

[1.0.2] - skipped

Added more tests; mangled private attributes in multiple classes; made some refactors; implemented iters.group_from, iters.awindowed_complete, iters.aall_unique, iters.anth_product, iters.anth_permutation, iters.anth_combination_with_replacement.

[1.0.1] - 2026-06-30

Implemented util.evaluate_and_return, iters.awrapf, and exceptions.ignore_warnings; added reject_cb and await_cb parameters to iters.aguessmax and iters.aguessmin; added yield_sentinel keyword argument to util.aiter_from_f.

[1.0.0] - 2026-06-26; first stable version

Added some tests; enabled some pydocstyle lint rules; refactored internal modules to avoid importing asyncio to show the help message and library version; moved warnings badge generation to slower test run; switched back to codecov due to pricing; integrated spelling checker.

Below versions are unstable

[0.9]

Breaking changes:

  • Declared end of life for all alpha versions.

  • Changed version shelving and unshelving schema.

  • Finalized the following top level objects:

    Constants:

    • __version__

    • __hexversion__

    • submodules_map

    • preloaded_submodules

    • console_preloaded_submodules

    Functions:

    • time_since_boot

  • Declared the following submodules and symbols as part of the public API:

    • altlocks

      Classes:

      • CircuitBreaker

      • DynamicThrottle

      • Releasing

      • ResourceGuard

      • StatefulBarrier

      • UniqueResourceGuard

    • base

      Classes:

      • event_loop (context manager)

      Functions:

      • adisembowel

      • adisembowel_left

      • aenumerate

      • aiter_to_gen

      • collect

      • collect_into

      • drop

      • iter_to_agen

      • safe_cancel_batch

      • sleep_forever

      • take

      Awaitables:

      • dummy_task

      • yield_to_event_loop

    • buckets

      Classes:

      • LeakyBucket

      • TokenBucket

    • channels

      Classes:

      • EventBus

      • Observable

      • Rendezvous

    • cli

      Functions:

      • run

    • compete

      Functions:

      • convert_to_coro_iter

      • enhanced_gather

      • enhanced_staggered_race

      • first_completed

      • multi_winner_race_with_callback

      • race_with_callback

    • config

      Classes:

      • Debugging

      • Executor

      Functions:

      • get_past_logs

      • set_logger_level

      Configuration values:

      • basic_repl

      • debug

      • loaded_all

      • logging_to

      • max_memory_errors

      • pdb

      • silent

    • console

      Classes:

      • AsyncUtilsConsole

      • ConsoleBase

    • constants

      Classes:

      • SentinelBase

      Constants:

      • EXECUTORS_FROZENSET

      • POSSIBLE_EXECUTORS

      • RECIPROCAL_E

      Sentinels:

      • RAISE

    • context

      Classes:

      • Context

      • LocalContext (context manager)

      • NonReusableLocalContext (context manager)

      Constants:

      • all_contextual_consts

      • … (every constant in the all_contextual_consts frozenset)

      Functions:

      • getcontext

      • setcontext

    • events

      Classes:

      • SingleWaiterEventWithValue

      • EventWithValue

    • exceptions:

      Classes:

      • ref

      • IgnoreErrors

      • WarningToError

      Constants:

      • CRITICAL

      Context managers (ignore_*):

      • ignore_all

      • ignore_noncritical

      • ignore_typical

      • ignore_stop_iteration

      • ignore_stop_async_iteration

      • ignore_valerrs

      • ignore_typeerrs

      Exception types:

      • Critical

      • StateCorrupted

      • VersionError

      • VersionConversionError

      • VersionNormalizerMissing

      • VersionCorrupted

      • VersionValueError

      • VersionNormalizerTypeError

      • VersionNormalizerFault

      • BulkheadError

      • BulkheadFull

      • BulkheadShutDown

      • PoolError

      • PoolFull

      • PoolShutDown

      • RateLimitExceeded

      • BusError

      • BusTimeout

      • BusShutDown

      • BusStatsErrors

      • BusPublishingError

      • CircuitBreakerError

      • CircuitHalfOpen

      • CircuitOpen

      • EventValueError

      • FutureCorrupted

      • MaxIterationsError

      • Deadlock

      • ResourceBusy

      • ItemsExhausted

      • LockForceRequest

      • PasswordQueueError

      • PasswordRetrievalError

      • GetPasswordRetrievalError

      • PutPasswordRetrievalError

      • ForbiddenOperation

      • PasswordError

      • WrongPassword

      • WrongPasswordType

      • PasswordMissing

      • GetPasswordMissing

      • PutPasswordMissing

      Functions:

      • unnest

      • unnest_reverse

      • potent_derive

      • prepare_exception

      • raise_exc

      • exception_occurred

      • wrap_exc

      • unwrap_exc

    • func

      Classes:

      • RateLimited

      Functions:

      • areduce

      • iterf

      • acompose

      • every

      • everymethod

      • timer

      • retry

      • throttle

      • debounce

      • measure

      • measure2

      • benchmark

      • star

      • unstar

    • futures

      Classes:

      • AsyncCallbacksFuture

      • AsyncCallbacksTask

      • TimeAwareAsyncCallbacksFuture

      • TimeAwareAsyncCallbacksTask

      • TimeAwareFuture

      • TimeAwareTask

      • TimeAwareUniqueCallbacksFuture

      • TimeAwareUniqueCallbacksTask

      • UniqueCallbacksFuture

      • UniqueCallbacksTask

    • iotools

      Classes:

      • AsyncReadWriteCouple

      • MemoryMappedIOManager

      Functions:

      • double_ended_text_pipe

      • double_ended_binary_pipe

    • iterclasses

      Classes:

      • AChain

      • APeekable

      • ABucket

    • iters

      Functions:

      • … (There are too many of these, so just refer to the IDE autocomplete or read the stub)

    • locks

      Classes:

      • AdvancedRateLimit

      • DynamicBoundedSemaphore

      • PrioritySemaphore

      • KeyedCondition

      • RLock

      • PriorityLock

      • PriorityRLock

      • MultiCountDownLatch

    • locksmiths

      Classes:

      • LocksmithBase

      Enumerations:

      • ForceResult

      • RecognitionResult

      Functions:

      • succeeded

    • misc

      Classes:

      • CallbackAccumulator

      • StateMachine

      • CacheWithBackgroundRefresh

      Functions:

      • gather_with_limited_concurrency

    • mixins

      Interfaces/Mixins:

      • LoopContextMixin

      • AwaitableMixin

      • AsyncContextMixin

      • ExecutorRequiredAsyncContextMixin

      • LockMixin

      • LockWithOwnerMixin

      • EventMixin

    • networking

      Classes:

      • LineProtocol

      • LFProtocol

      • CRLFProtocol

      • CRProtocol

      • SocketTransport

    • pools

      Classes:

      • AdvancedPool

      • ConnectionPool

    • processors

      Classes:

      • BoundedBatchProcessor

      • BatchProcessor

      • Bulkhead

    • properties

      Classes:

      • AsyncPropertyBase

      • ConcurrentAsyncProperty

      • LazyAsyncProperty

      • RWLockedAsyncProperty

      Enumerations:

      • Deleters

    • queues

      Interfaces:

      • PotentQueueBase

      Classes:

      • SmartQueue

      • SmartLifoQueue

      • SmartPriorityQueue

      • UserPriorityQueue

      Functions:

      • password_queue

      Context managers (ignore_*):

      • ignore_qshutdown

      • ignore_qempty

      • ignore_qfull

      • ignore_qerrs

    • rwlocks

      Classes:

      • RWLock

      • FairRWLock

      • ReadPreferredRWLock

      • WritePreferredRWLock

      • PriorityRWLock

      • FairPriorityRWLock

      • WritePreferredPriorityRWLock

      • AgingRWLock

      • CoercedMethod

    • signals

      Functions:

      • wait_for_signal

    • tools

      Functions:

      • loadf

      • json_to_argv

      • json_to_argstr

      • argv_to_json

      • argstr_to_json

      • get_cfg_json_format

      • print_cfg_json_format

      • get_cmd_help

      • print_cmd_help

    • util

      Context managers (ignore_*):

      • ignore_cancellation

      Context manager classes:

      • anullcontext

      Functions:

      • aawcmf2dcmf

      • aawcmf2dcmff

      • afcopy

      • dcm

      • discard_retval

      • get_future

      • make_task_factory

      • new_eager_tasks

      • to_sync

      • to_async

      • to_sync_from_loop

      • sync_await

      • lockf

      • done_evt

      • done_fut

      • locked_lock

      • dualcontextmanager

      • semaphore

      • aiter_from_f

      • safe_cancel

      • transient_block

      • transient_block_from_loop

      • wrap_in_coro

      • atruthify

      • afalsify

      • anullify

      • avalify

    • version

      Classes:

      • VersionInfo

      • VersionDelta

      Functions:

      • normalize

      • normalize_allow_unimplemented

      • register_normalizer

      • unregister_normalizer

      • dispatch_normalizer

      • autogenerate_normalizers

[0.9.16] - 2026-06-22

Greatly improved futures and properties functionality.

[0.9.15] - 2026-06-17

Committed uv.lock to version control; replaced AsyncGenerator with AsyncGeneratorType and Generator with GeneratorType where appropriate.

[0.9.14] - 2026-06-13

Refactored base.event_loop; improved submodule logging and __dir__ method handling.

[0.9.13] - 2026-06-12

Reorganized the project structure; added a test; clarified documentation.

[0.9.12] - 2026-06-10

Fixed all warnings in Sphinx nitpicky builds; declared free-threaded support as standard; unpinned the exact beta of Python 3.15.

[0.9.11] - 2026-06-04

Upgraded to Python 3.15.0b2; added experimental GraalPy and free-threaded support.

[0.9.10] - 2026-05-29

Integrated CodeQL fully.

[0.9.9] - 2026-05-26

Added more tests and more badges to the readme; removed codecov upload step superseded by GitHub Code Quality.

[0.9.8] - 2026-05-23

Added the genmakefileusage scripts, among some rewrites, most notably eliminating instances of a bare Any annotating an argument.

[0.9.7] - 2026-05-21

Added locksmiths submodule.

[0.9.6] - 2026-05-19

Re-committed .markdownlint.json to version control; documentation nears completion; used GitHub Actions for page deployment.

[0.9.5] - 2026-05-17

Some bugfixes; began deployment to GitHub Pages.

[0.9.4] - 2026-05-15

Fixed workflows once more and integrated uv more fully; migrated from mypy to ty, removing stubtest step.

[0.9.3] - 2026-05-11

Added some tests; changed symbolic links to a copy step in the Read the Docs build, which is more reliable; fixed codecov trigger; added sphinx-copybutton as an optional dependency.

[0.9.2] - 2026-05-07

Created symbolic links in docs directory linking to root .md files; fixed some bugs; respected some more environment variables and documented this behaviour; completed benchmarks; added myst_parser as an optional dependency; bumped some dependencies; added some examples.

[0.9.1] - 2026-05-01

Declared full support for python[ -m] asyncutils an entry point; patched function, method and class method signatures where appropriate; added -P/–pdb option; switched to furo theme.

[0.9.0] - 2026-04-27

Added __lazy_modules__ attribute to submodules where appropriate; added some iteration, functional programming and context management utilities.

Below versions have reached EOL

[0.8]

Breaking changes:

[0.8.28] - 2026-04-24

Rewrote submodules loading mechanism; removed fragile relative imports; compressed asyncio and sibling module imports to avoid overhead.

[0.8.27] - 2026-04-21

Added more tests and fixed stubtest errors; abolished slow markdownlint step in pre-commit; various API additions.

[0.8.26] - 2026-04-18

Squashed many bugs and stub inaccuracies; integrated stubtest; simplified workflows; added more contextual constants.

[0.8.25] - 2026-04-14

Created issue templates.

[0.8.24] - 2026-04-10

Created AI_USAGE_POLICY.md.

[0.8.23] - 2026-04-09

Integrated pre-commit CI.

[0.8.22] - 2026-04-05

Created the audit events table.

[0.8.21] - 2026-04-01

Organized badges into table; started using mypy.

[0.8.20] - 2026-03-29

Started hosting documentation on Read the Docs.

[0.8.19] - 2026-03-27

Set up docs directory.

[0.8.17] - 2026-03-24

Started using detect-secrets.

[0.8.16] - 2026-03-22

Started using ruff; created py.typed.

[0.8.14] - 2026-03-21

Set up tests directory; started using pytest.

[0.8.9] - 2026-03-14

Created Dockerfile.

[0.8.8] - 2026-03-12

Created .editorconfig and .pre-commit-config.yaml.

[0.8.6] - 2026-03-10

Created ROADMAP.md.

[0.8.4] - 2026-03-09

Created SUPPORT.md and CHANGELOG.md.

[0.8.2] - 2026-03-07

Created CODE_OF_CONDUCT.md and CONTRIBUTING.md.

[0.8.1] - 2026-03-06

Created pyproject.toml and SECURITY.md.

[0.8.0] - 2026-03-06

Set up git; added version submodule.

Below entries are abridged

[0.7] - 2026-02-09

Began migration of implementation details into _internal subpackage; fixed initialization logic and command line.

[0.6] - 2026-01-1x

Completed migration from inline annotations to separated stubs; perfected base.event_loop and lazy loading; added console and cli submodules.

[0.5] - 2025-12-0x

Added classes such as altlocks.CircuitBreaker and channels.EventBus; implemented preliminary lazy loading system; created exceptions submodule; began separation of type annotations from .py into .pyi.

[0.4] - 2025-10-0x

Added more complicated patterns and procedures such as channels.Observable and signals.wait_for_signal.

[0.3] - 2025-08-2x

Basically completed refactoring; added more object-oriented patterns such as altlocks.DynamicThrottle and misc.CacheWithBackgroundRefresh.

[0.2] - 2025-07-0x

Began reorganizing single file containing all functions into submodules.

[0.1] - 2025-06-xx

Added basic but untested features such as iters.tee, iters.merge, base.to_async, base.iter_to_agen and util.sync_await.

[0.0] - 2025-05

Development began. This can be classified as a passion project.

Roadmap

This file provides an overview of the direction towards which this project is heading.

Current version: 1.1.0

[1.x]

  • Enhance the test suite

  • Incorporate user feature requests

[2.x]

  • Increase coverage to 75%

[3.0] - 2027-10 or before

  • Comprehensive bugfixes

  • Deprecate Python <=3.12 compatibility module

  • Ramp up coverage to 90%

  • Remove or supersede faulty patterns

[3.x]

  • Major feature additions, with more focus on the low level

  • Publish docker images if there is demand

[4.0] - 2028-06

  • Set up funding

  • Deprecate Python <=3.13 compatibility module

[5.0] - 2029-02

  • Drop support for Python 3.12 (adapt type parameters with defaults)

[6.0] - 2029-10

  • Drop support for Python 3.13 (remove functools.partial compatibility layer)

  • Synchronize release schedule with Python’s (major release every Python minor version)

Note

This project is being actively developed and maintained. It currently only fully supports CPython 3.12 or above.

Note

The format of this page was inspired by pytest.