pyee is a rough port of node.js’s EventEmitter. Unlike its namesake, it includes a number of subclasses useful for implementing async and threaded programming in python, such as async/await as seen in python 3.5+.
You can install this project into your environment of choice using
pip install pyee
pyee supplies a
BaseEventEmitter class that is similar to the
EventEmitter class from Node.js. In addition, it supplies the subclasses
for supporting async and threaded execution with asyncio, twisted, and
concurrent.futures Executors respectively, as supported by the environment.
In : from pyee import BaseEventEmitter In : ee = BaseEventEmitter() In : @ee.on('event') ...: def event_handler(): ...: print('BANG BANG') ...: In : ee.emit('event') BANG BANG In :
The base event emitter class. All other event emitters inherit from this class.
Most events are registered with an emitter via the
oncemethods, and fired with the
emitmethod. However, pyee event emitters have two special events:
new_listener: Fires whenever a new listener is created. Listeners for this event do not fire upon their own creation.
error: When emitted raises an Exception by default, behavior can be overriden by attaching callback to the event.
@ee.on('error') def on_error(message): logging.err(message) ee.emit('error', Exception('something blew up'))
All callbacks are handled in a synchronous, blocking manner. As in node.js, raised exceptions are not automatically handled for you—you must catch your own exceptions, and treat them accordingly.
emit(event, *args, **kwargs)¶
**kwargsto each attached function. Returns
Trueif any functions are attached to
event; otherwise returns
datais an attached function, this will call
Returns a list of all listeners registered to the
Registers the function
fto the event name
fisn’t provided, this method returns a function that takes
fas a callback; in other words, you can use this method as a decorator, like so:
@ee.on('data') def data_handler(data): print(data)
In both the decorated and undecorated forms, the event handler is returned. The upshot of this is that you can call decorated handlers directly, as well as use them in remove_listener calls.
The same as
ee.on, except that the listener is automatically removed after being called.
Remove all listeners attached to
None, remove all listeners on all events.
Removes the function
An event emitter class which can run asyncio coroutines in addition to synchronous blocking functions. For example:
@ee.on('event') async def async_handler(*args, **kwargs): await returns_a_future()
On emit, the event emitter will automatically schedule the coroutine using
asyncio.ensure_futureand the configured event loop (defaults to
Unlike the case with the BaseEventEmitter, all exceptions raised by event handlers are automatically emitted on the
errorevent. This is important for asyncio coroutines specifically but is also handled for synchronous functions for consistency.
loopis specified, the supplied event loop will be used when scheduling work with
ensure_future. Otherwise, the default asyncio event loop is used.
For asyncio coroutine event handlers, calling emit is non-blocking. In other words, you do not have to await any results from emit, and the coroutine is scheduled in a fire-and-forget fashion.
An event emitter class which can run twisted coroutines and handle returned Deferreds, in addition to synchronous blocking functions. For example:
@ee.on('event') @inlineCallbacks def async_handler(*args, **kwargs): yield returns_a_deferred()
@ee.on('event') async def async_handler(*args, **kwargs): await returns_a_deferred()
When async handlers fail, Failures are first emitted on the
failureevent. If there are no
failurehandlers, the Failure’s associated exception is then emitted on the
errorevent. If there are no
errorhandlers, the exception is raised. For consistency, when handlers raise errors synchronously, they’re captured, wrapped in a Failure and treated as an async failure. This is unlike the behavior of BaseEventEmitter, which have no special error handling.
For twisted coroutine event handlers, calling emit is non-blocking. In other words, you do not have to await any results from emit, and the coroutine is scheduled in a fire-and-forget fashion.
Similar behavior occurs for “sync” functions which return Deferreds.
An event emitter class which runs handlers in a
concurrent.futuresexecutor. If using python 2, this will fall back to trying to use the
futuresbackported library (caveats there apply).
By default, this class creates a default
ThreadPoolExecutor, but a custom executor may also be passed in explicitly to, for instance, use a
This class runs all emitted events on the configured executor. Errors captured by the resulting Future are automatically emitted on the
errorevent. This is unlike the BaseEventEmitter, which have no error handling.
The underlying executor may be shut down by calling the
shutdownmethod. Alternately you can treat the event emitter as a context manager:
with ExecutorEventEmitter() as ee: # Underlying executor open @ee.on('data') def handler(data): print(data) ee.emit('event') # Underlying executor closed
Since the function call is scheduled on an executor, emit is always non-blocking.
No effort is made to ensure thread safety, beyond using an executor.
shutdownon the internal executor.
CompatEventEmitter(scheduler=<function ensure_future>, loop=None)¶
An EventEmitter exposed for compatibility with prior versions of pyee. This functionality is deprecated; you should instead use either
This class is similar to the
AsyncIOEventEmitterclass, but also allows for overriding the scheduler function (
ensure_futureby default as in
ASyncIOEventEmitter) and does duck typing checks to handle Deferreds. In other words, by setting
twisted.internet.defer.ensureDeferredthis will support twisted use cases for coroutines.
When calling synchronous handlers, raised exceptions are ignored - as with the BaseEventEmitter, you must capture and handle your own exceptions. However, for coroutine functions, exceptions are handled by emitting them on the
errorevent. Note that when using with twisted, the
errorevent will emit Failures, not Exceptions.
This class will also successfully import in python 2, but without coroutine support.