Skip to main content

Distributed event bus with Redis pub/sub, source-instance dedup, and pre-rehydration buffering

Project description

nodus-events

Distributed event bus with Redis pub/sub, source-instance deduplication, and pre-rehydration buffering.

Local-first: events are recorded in the in-process AuditStore and optionally broadcast over Redis pub/sub when [redis] is installed. No required external dependencies — the bus works fully in local mode without Redis.

Status: v0.1.0 — prepared, not yet published.


Install

pip install nodus-events

# With Redis pub/sub support:
pip install "nodus-events[redis]"

What it provides

Component Purpose
EventBus Publish events locally and optionally via Redis pub/sub
EventBusConfig Connection settings, channel, instance ID, buffer config
Event Typed event record with type, payload, correlation ID, timestamp
AuditStore / InMemoryAuditStore Persistent event log (protocol + in-memory impl)
get_event_bus() Process-level singleton factory
publish_event() Convenience wrapper for one-line event emission

Quick start

from nodus_events import publish_event, get_event_bus

# One-liner emission (uses process singleton)
publish_event("user.created", payload={"user_id": "u123"}, correlation_id="req-abc")

# Direct bus access
bus = get_event_bus()
bus.publish("flow.completed", payload={"flow_id": "f1"})

# Read audit log
events = bus.audit_store.list()

Redis pub/sub

from nodus_events import EventBusConfig, get_event_bus

config = EventBusConfig(
    redis_url="redis://localhost:6379",
    channel="nodus:events",
    instance_id="worker-1",   # dedup: ignores events from own instance
)

bus = get_event_bus(config)
bus.start_subscriber(callback=lambda event: print(event.event_type))

Events published by this instance are not re-delivered to its own subscriber — source_instance_id deduplication prevents echo loops.

Stop the subscriber and flush buffered events:

bus.stop()
buffered = bus.drain_buffered_events()   # events received before start_subscriber()

Pre-rehydration buffering

Events that arrive over Redis before start_subscriber() is called are buffered in memory. drain_buffered_events() returns them in order after the subscriber starts — no events are lost during startup.


EventBusConfig

from nodus_events import EventBusConfig

config = EventBusConfig(
    redis_url=None,           # None → local-only mode (no Redis)
    channel="nodus:events",   # Redis pub/sub channel name
    enabled=True,
    instance_id="worker-1",   # unique per process/pod
    reconnect_delay_secs=5,
    max_buffer_size=1000,
)

Event record

from nodus_events import Event

# Event fields:
event.event_type          # str
event.correlation_id      # str | None
event.source_instance_id  # str
event.payload             # dict | None
event.timestamp           # float (UTC epoch seconds)

AuditStore protocol

from nodus_events import AuditStore, InMemoryAuditStore

store = InMemoryAuditStore()
store.record(event)
events = store.list()                    # all events
events = store.list(event_type="user.created")
events = store.list(limit=50)

Implement AuditStore to back the log with a database.


Singleton management

from nodus_events import get_event_bus, reset_event_bus

bus = get_event_bus(config)   # creates singleton on first call
bus2 = get_event_bus()        # returns same instance (config ignored)

# In tests — reset between cases:
reset_event_bus()

Design

  • No required dependencies. Local mode works with zero extras. Redis is opt-in via [redis] extra.
  • Source-instance dedup. Each bus has a unique instance_id; events it published are not re-delivered to itself.
  • Pre-rehydration buffer. Events arriving before start_subscriber() are buffered so no events are dropped during startup.
  • Thread-safe. Singleton creation and audit store use threading.Lock.

Development

pip install -e ".[dev]"
pytest tests/ -q

License

MIT — see LICENSE.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

nodus_events-0.1.0.tar.gz (11.0 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

nodus_events-0.1.0-py3-none-any.whl (9.3 kB view details)

Uploaded Python 3

File details

Details for the file nodus_events-0.1.0.tar.gz.

File metadata

  • Download URL: nodus_events-0.1.0.tar.gz
  • Upload date:
  • Size: 11.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.9

File hashes

Hashes for nodus_events-0.1.0.tar.gz
Algorithm Hash digest
SHA256 50695d1c90bbe868729590b2b266c4192301e65b054deada31f478c86a369335
MD5 44186711faebbc7a844945668f29f551
BLAKE2b-256 c4752f1e0d49461ce71bc50709ef04aeb9d900d0549379e1c550bbef4425d2a5

See more details on using hashes here.

File details

Details for the file nodus_events-0.1.0-py3-none-any.whl.

File metadata

  • Download URL: nodus_events-0.1.0-py3-none-any.whl
  • Upload date:
  • Size: 9.3 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.9

File hashes

Hashes for nodus_events-0.1.0-py3-none-any.whl
Algorithm Hash digest
SHA256 a79643c947cd5c75d1730470d970cd17665f68d8e3705611f8dbd1a6e411f524
MD5 24edccd6fda2b21b21e2045ab5cfabba
BLAKE2b-256 d771e6d6dec3e5c65c9b15ec84ef68d05078f572962d89a6dfeed8486ade61b7

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page