Skip to content

msflib.eventbus

Part of the msflib core package.

msflib.eventbus

InProcessEventTransport(target: EmitterTarget = emitter)

Transport adapter that forwards events to the in-process eventbus.

AppEmitter(instance: Emitter)

Developer-facing emitter bound to an app or explicit emitter instance.

This is a thin wrapper around the underlying emitter instance and mirrors pyee-style method signatures.

listen(event_name: EventKey)

Decorator-style listener registration with contextual logger injection.

Emitter(loop: asyncio.AbstractEventLoop | None = None)

Bases: AsyncIOEventEmitter

Synchronous in-process event emitter.

Note: this wrapper is built on pyee.asyncio.AsyncIOEventEmitter. Async listeners are scheduled by pyee, and exceptions raised inside async listeners are surfaced through pyee's error event behavior.

emit_optional(event: EventKey, *args, **kwargs) -> bool

Emit event if listeners exist; warn and continue on listener failures.

Async listener failures are handled through pyee's error-event behavior.

emit_optional_async(event: EventKey, *args, **kwargs) -> bool async

Emit event and await async listeners when running in an async context.

emit_required(event: EventKey, *args, **kwargs) -> bool

Emit event and require at least one successful listener path.

Note: for asynchronous listeners, failures are surfaced through pyee's error-event behavior and cannot be caught synchronously by this method.

emit_strict(event: EventKey, *args, raise_error: bool = True, **kwargs) -> bool | Exception

Emit event; do not require listeners but raise or return listener errors.

If no listeners are registered this returns False. If any synchronous listener raises an exception then:

  • when raise_error is True (default) the original exception is re-raised so callers using this library receive the actual error;
  • when raise_error is False the exception instance is returned instead of being raised.

This synchronous API does not execute async listeners.

Async listeners or awaitable return values are not supported here and will always raise EventBusAsyncListenerNotSupportedError (regardless of raise_error). Use emit_strict_async in async call paths.

emit_strict_async(event: EventKey, *args, raise_error: bool = True, **kwargs) -> bool | Exception async

Async variant of emit_strict that awaits async listeners.

Returns False when there are no listeners. On listener failure the original exception is re-raised when raise_error is True (default), otherwise the exception instance is returned.

emit_required_async(event: EventKey, *args, **kwargs) -> bool async

Emit event, requiring at least one listener, and await async listeners.

EventBusAsyncListenerNotSupportedError

Bases: EventBusError

Raised when an async listener is improperly attached or encountered during a synchronous emit.

EventBusError

Bases: Exception

Base class for eventbus-specific errors.

HookRegistry()

Track per-emitter listener bindings and support deterministic reset.

bind_app_emitter(app: Any | None = None, instance: Emitter | None = None) -> AppEmitter

Bind an emitter to an app and activate it for each request.

Call this once during app creation so each app instance has isolated listener state and per-request event dispatch.

configure_eventbus_logger(*, handler: logging.Handler | None = None, formatter: logging.Formatter | None = None, level: int | None = None, propagate: bool | None = None, replace_handlers: bool = False) -> logging.Logger

Configure EventBus logging explicitly from the host application.

The eventbus library does not attach a stream handler by default. Use this helper when you want a custom formatter/handler for EventBus logs.

listen(event_name: EventKey, *, app: Any | None = None, instance: Any | None = None)

Decorator for listener registration.

Default behavior preserves legacy global registration. For modular, testable integrations, pass app=... or instance=... to bind listeners to a specific app/emitter scope.

resolve_emitter(*, app: Any | None = None, instance: Any | None = None) -> Emitter

Resolve an effective emitter from app/instance/global inputs.

This keeps module-level hook registration logic consistent across packages.

use_emitter(instance: Emitter)

Temporarily bind an emitter to the current context.

Background tasks run after the request middleware context has exited, so they should wrap their work in with use_app_emitter(app): or an equivalent explicit emitter scope if they need the app-scoped listeners.

extract_changed_fields(update_data: Any) -> list[str]

Return explicitly provided fields from an update payload.

merge_event_contracts(*maps: Mapping[str, type[Any]]) -> dict[str, type[Any]]

Merge module event contract maps into a single registry.

Later maps override earlier maps for duplicate event names.

adapter

InProcessEventTransport(target: EmitterTarget = emitter)

Transport adapter that forwards events to the in-process eventbus.

base

EventBusError

Bases: Exception

Base class for eventbus-specific errors.

EventBusAsyncListenerNotSupportedError

Bases: EventBusError

Raised when an async listener is improperly attached or encountered during a synchronous emit.

Emitter(loop: asyncio.AbstractEventLoop | None = None)

Bases: AsyncIOEventEmitter

Synchronous in-process event emitter.

Note: this wrapper is built on pyee.asyncio.AsyncIOEventEmitter. Async listeners are scheduled by pyee, and exceptions raised inside async listeners are surfaced through pyee's error event behavior.

emit_optional(event: EventKey, *args, **kwargs) -> bool

Emit event if listeners exist; warn and continue on listener failures.

Async listener failures are handled through pyee's error-event behavior.

emit_optional_async(event: EventKey, *args, **kwargs) -> bool async

Emit event and await async listeners when running in an async context.

emit_required(event: EventKey, *args, **kwargs) -> bool

Emit event and require at least one successful listener path.

Note: for asynchronous listeners, failures are surfaced through pyee's error-event behavior and cannot be caught synchronously by this method.

emit_strict(event: EventKey, *args, raise_error: bool = True, **kwargs) -> bool | Exception

Emit event; do not require listeners but raise or return listener errors.

If no listeners are registered this returns False. If any synchronous listener raises an exception then:

  • when raise_error is True (default) the original exception is re-raised so callers using this library receive the actual error;
  • when raise_error is False the exception instance is returned instead of being raised.

This synchronous API does not execute async listeners.

Async listeners or awaitable return values are not supported here and will always raise EventBusAsyncListenerNotSupportedError (regardless of raise_error). Use emit_strict_async in async call paths.

emit_strict_async(event: EventKey, *args, raise_error: bool = True, **kwargs) -> bool | Exception async

Async variant of emit_strict that awaits async listeners.

Returns False when there are no listeners. On listener failure the original exception is re-raised when raise_error is True (default), otherwise the exception instance is returned.

emit_required_async(event: EventKey, *args, **kwargs) -> bool async

Emit event, requiring at least one listener, and await async listeners.

AppEmitter(instance: Emitter)

Developer-facing emitter bound to an app or explicit emitter instance.

This is a thin wrapper around the underlying emitter instance and mirrors pyee-style method signatures.

listen(event_name: EventKey)

Decorator-style listener registration with contextual logger injection.

HookRegistry()

Track per-emitter listener bindings and support deterministic reset.

configure_eventbus_logger(*, handler: logging.Handler | None = None, formatter: logging.Formatter | None = None, level: int | None = None, propagate: bool | None = None, replace_handlers: bool = False) -> logging.Logger

Configure EventBus logging explicitly from the host application.

The eventbus library does not attach a stream handler by default. Use this helper when you want a custom formatter/handler for EventBus logs.

resolve_emitter(*, app: Any | None = None, instance: Any | None = None) -> Emitter

Resolve an effective emitter from app/instance/global inputs.

This keeps module-level hook registration logic consistent across packages.

use_emitter(instance: Emitter)

Temporarily bind an emitter to the current context.

Background tasks run after the request middleware context has exited, so they should wrap their work in with use_app_emitter(app): or an equivalent explicit emitter scope if they need the app-scoped listeners.

bind_app_emitter(app: Any | None = None, instance: Emitter | None = None) -> AppEmitter

Bind an emitter to an app and activate it for each request.

Call this once during app creation so each app instance has isolated listener state and per-request event dispatch.

listen(event_name: EventKey, *, app: Any | None = None, instance: Any | None = None)

Decorator for listener registration.

Default behavior preserves legacy global registration. For modular, testable integrations, pass app=... or instance=... to bind listeners to a specific app/emitter scope.

events

merge_event_contracts(*maps: Mapping[str, type[Any]]) -> dict[str, type[Any]]

Merge module event contract maps into a single registry.

Later maps override earlier maps for duplicate event names.

extract_changed_fields(update_data: Any) -> list[str]

Return explicitly provided fields from an update payload.