Skip to main content

xtr-event-dispatcher-contracts

The event dispatching contract, and nothing else — so a library that emits events installs nothing else.

python 3.11+ asyncio core dependencies: 0 typed license MIT

Why?

A library that announces what happened — an order placed, a message consumed — should not decide who hears it. It takes an event dispatcher, hands it an event object, and leaves the listeners to the application that wires it. That needs the contract, not a dispatcher:

  • 📣 EventDispatcherInterface — await dispatcher.dispatch(event), and the event comes back.
  • 🛑 Event / StoppableEventInterface — an event any listener can stop.
  • 🔎 ListenerIntrospectionInterface — which listeners an event has, and in which order.
  • 🧷 Listener and event_name_of() — what a listener is called with, and the name an event is known by.
  • 🪶 No dependencies.
from dataclasses import dataclass

from xtr_event_dispatcher_contracts import Event, EventDispatcherInterface


@dataclass(frozen=True)
class MessageConsumed(Event):
    message_id: str


class Worker:
    def __init__(self, events: EventDispatcherInterface) -> None:
        self._events = events

    async def handled(self, message_id: str) -> None:
        await self._events.dispatch(MessageConsumed(message_id))

Install

uv add xtr-event-dispatcher-contracts

Requires Python 3.11+.

Who installs what

Depends on
A library that emits events xtr-event-dispatcher-contracts at runtime.
An application xtr-event-dispatcher, which implements this contract and wires listeners from a container.

xtr-event-dispatcher re-exports Event, StoppableEventInterface, ListenerIntrospectionInterface, Listener and event_name_of rather than redefining them, so a library written against this package and an application using that one share the same objects. Its own EventDispatcherInterface extends the one here with registering listeners.

The contract

class EventDispatcherInterface(Protocol):
    async def dispatch(self, event: T, event_name: str | type | None = None) -> T: ...
  • Names. Events are keyed by name: a string, or a class standing for "<module>.<qualname>" (event_name_of). Without a name, an event is dispatched under its class's.
  • Order. Listeners run highest priority first, one after the other, each awaited before the next. An exception a listener raises reaches the caller unchanged.
  • Stopping. An event that is a StoppableEventInterface stops reaching listeners once one stops it. Event is the base class that does this, frozen dataclasses included: event.stop_propagation().
  • Listeners (Listener) are called with the event, its name and the dispatcher — as many of the three as they take, by position; an awaitable result is awaited.

ListenerIntrospectionInterface reads listeners without registering any: get_listeners(name) in running order (or every event's, given no name), get_listener_priority(name, listener), has_listeners(name=None).

Development

Developed in the python-xtr monorepo, under packages/xtr-event-dispatcher-contracts; run the commands below from there. The python-xtr-event-dispatcher-contracts repository is a read-only copy, so send issues and pull requests to the monorepo.

uv sync
uv run ruff check && uv run ruff format --check && uv run basedpyright && uv run ty check && uv run pytest

License

MIT — see LICENSE.

Metadata

Release files for xtr-event-dispatcher-contracts 3.0.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for xtr-event-dispatcher-contracts 3.0.0
File Size Uploaded
xtr_event_dispatcher_contracts-3.0.0.tar.gz 7.5 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for xtr-event-dispatcher-contracts 3.0.0
File Interpreter ABI Platform
xtr_event_dispatcher_contracts-3.0.0-py3-none-any.whl Python 3 none any Details

Total release size: 17.8 kB

Release files / xtr_event_dispatcher_contracts-3.0.0.tar.gz

Download URL xtr_event_dispatcher_contracts-3.0.0.tar.gz
Size 7.5 kB
Tags Source
SHA-256 checksum
How to use checksums
250c1cac259a871f687618166dec57258403d551885ca98a760e64a5c7f18bd6
BLAKE2b-256 checksum
How to use checksums
625afa4f452fd944169291ba9d94647893c6e1dc345e4235f9bdfbd537da5667
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 5, 2026.

Transparency log

Release files / xtr_event_dispatcher_contracts-3.0.0-py3-none-any.whl

Download URL xtr_event_dispatcher_contracts-3.0.0-py3-none-any.whl
Size 10.3 kB
Tags Python 3
SHA-256 checksum
How to use checksums
e00ac8465b9fc2166f9f7cfb346a8dae757416e476946861c46dd21bce549859
BLAKE2b-256 checksum
How to use checksums
be65d3d9f6f4579f24cca75d36edec5c81788dedd1c1961a66d1cecad2dc1070
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 5, 2026.

Transparency log

Release history Release notifications | RSS feed

4.1.0

2 release files

4.0.4

2 release files

4.0.3

2 release files

4.0.2

2 release files

This release

3.0.0 This release

2 release files

2.0.0

2 release files

1.5.0

2 release files

1.4.0

2 release files

1.3.0

2 release files

1.2.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page