Skip to main content

High-performance event sourcing library combining Rust performance with Python ease of use

Project description

Onyx Octopus

Eventuali (Onyx Octopus): High-performance event sourcing library for Python, powered by Rust.

Why Eventuali?

Problem: Pure Python event sourcing hits performance walls at scale. Complex financial calculations, high-throughput IoT streams, and real-time analytics demand more than Python alone can deliver.

Solution: Eventuali delivers Rust-level performance with Python-level simplicity - the only event sourcing library giving you 10-60x speed improvements without sacrificing developer experience.

# Same familiar Python code...
user.apply(UserRegistered(name="John", email="john@example.com"))
await store.save(user)

# ...but with 79,000+ events/second throughput
# 18.3x faster snapshot reconstruction  
# 186,000+ RBAC operations/second

Who Needs This?

๐Ÿฆ Fintech & Banking

  • Regulatory compliance requiring immutable audit trails (SOX, PCI DSS)
  • High-frequency trading with microsecond-sensitive operations
  • Real-time fraud detection processing millions of transactions
  • Financial reporting with historical state reconstruction

๐Ÿข Enterprise SaaS

  • Multi-tenant systems requiring strict data isolation
  • Real-time analytics dashboards with streaming updates
  • CQRS at scale with complex read model projections
  • Audit trails for compliance and security monitoring

๐Ÿ“ก IoT & Analytics

  • High-volume event ingestion from thousands of devices
  • Time-series analysis with historical event replay
  • Real-time monitoring of industrial systems
  • Edge computing with performance-critical processing

๐Ÿ”„ Microservices

  • Event-driven architecture requiring reliable event ordering
  • Distributed transactions with saga pattern coordination
  • Service decoupling through event-based communication
  • System observability with comprehensive event trails

Alternatives & Trade-offs

Pure Python Solutions

Library Pros Cons Best For
pyeventsourcing Mature, comprehensive Python ecosystem 10-60x slower, memory-intensive Simple applications, prototypes
Custom implementation Full control, tailored to needs High development cost, maintenance burden Specific niche requirements

Enterprise Platforms

Solution Pros Cons Best For
EventStore DB Proven at scale, rich querying Separate infrastructure, operational complexity Large enterprises with dedicated ops teams
Axon Framework Battle-tested, mature ecosystem Java-only, steep learning curve Java shops, complex domains
Apache Kafka Massive scale, proven reliability Stream-only (not event sourcing), complex setup Event streaming, not full event sourcing

Eventuali's Sweet Spot

โœ… Python teams needing enterprise performance
โœ… Single-library solution - no external infrastructure
โœ… Multi-database support - PostgreSQL, SQLite built-in
โœ… Production-ready - security, compliance, multi-tenancy included
โœ… Performance critical - 79K+ events/sec, 1M+ encryption ops/sec

When NOT to Use Eventuali

โŒ Skip if you have:

  • Simple CRUD applications - Traditional databases are simpler and sufficient
  • Early MVP/prototype stage - Event sourcing adds complexity during rapid iteration
  • Pure I/O bound workloads - Database bottlenecks limit Rust performance benefits
  • No event sourcing experience - Steep learning curve for teams new to the pattern
  • Extreme simplicity requirements - Event sourcing inherently adds architectural complexity

โœ… Perfect if you need:

  • Performance at Python scale (10K+ events/second)
  • Regulatory compliance with immutable audit trails
  • Complex domain logic with rich business rules
  • Historical analysis and temporal querying
  • Multi-tenant isolation with enterprise security

Performance vs Complexity Trade-off

           High Performance
                 โ–ฒ
     Eventuali   โ”‚   EventStore DB
         โ—       โ”‚       โ—
                 โ”‚   Axon Framework  
                 โ”‚       โ—
                 โ”‚
     Custom โ—โ”€โ”€โ”€โ”€โ”ผโ”€โ”€โ”€โ”€โ— pyeventsourcing
                 โ”‚
                 โ”‚
                 โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ–บ 
                Simple              Complex
                Implementation

Eventuali occupies the optimal position: High performance with manageable complexity for Python teams.

Overview

Eventuali combines the performance and memory safety of Rust with the developer experience of Python to create a powerful event sourcing library. It provides:

  • 10-60x performance improvement over pure Python implementations
  • 8-20x better memory efficiency
  • Multi-database support (PostgreSQL, SQLite)
  • Seamless Python integration with Pydantic models
  • Async/await support throughout
  • Type safety with full type hints

Architecture

  • Rust Core (eventuali-core): High-performance event storage, serialization, and projections
  • Python Bindings (eventuali-python): PyO3-based bindings with Pythonic APIs
  • Multi-Database: Unified interface supporting PostgreSQL and SQLite

Installation

Production Installation

# Install from PyPI (when available)
uv add eventuali

Development Installation

# Clone the repository
git clone git@github.com:primevalai/eventuali.git
cd eventuali/eventuali-python

# Install with development dependencies  
uv sync

# Install required tools
uv tool install maturin
uv tool install patchelf

# Build Python bindings
uv run maturin develop

# Verify installation
uv run python ../examples/01_basic_event_store_simple.py

Quick Start

import asyncio
from eventuali import EventStore, Aggregate, Event
from pydantic import BaseModel

# Define your events
class UserRegistered(Event):
    name: str
    email: str

class UserEmailChanged(Event):
    new_email: str

# Define your aggregate
class User(Aggregate):
    name: str = ""
    email: str = ""
    
    def apply_user_registered(self, event: UserRegistered) -> None:
        self.name = event.name
        self.email = event.email
    
    def apply_user_email_changed(self, event: UserEmailChanged) -> None:
        self.email = event.new_email

async def main():
    # Initialize the event store (SQLite for development)
    store = await EventStore.create("sqlite://events.db")
    
    # Create and save an aggregate
    user = User()
    user.apply(UserRegistered(name="John Doe", email="john@example.com"))
    await store.save(user)
    
    # Load and update the aggregate
    loaded_user = await store.load(User, user.id)
    loaded_user.apply(UserEmailChanged(new_email="john.doe@example.com"))
    await store.save(loaded_user)

asyncio.run(main())

Features

Multi-Database Support

# PostgreSQL for production
store = await EventStore.create(
    "postgresql://user:password@localhost/events"
)

# SQLite for development/testing
store = await EventStore.create("sqlite://events.db")

High-Performance Serialization

  • Protocol Buffers for maximum performance
  • JSON fallback for development and debugging
  • Automatic schema evolution support

Async Throughout

Built from the ground up with async/await support using Tokio (Rust) and asyncio (Python).

Development

This project uses a Rust/Python hybrid approach with UV as the mandated Python toolchain:

  1. Rust workspace with eventuali-core and eventuali-python
  2. Maturin for building Python wheels with embedded Rust
  3. PyO3 for seamless Rust-Python integration
  4. UV for all Python dependency management, tool installation, and script execution

UV Requirements

โš ๏ธ IMPORTANT: This project exclusively uses UV for Python operations.

UV provides faster, more reliable Python dependency management and ensures consistent environments across development and CI/CD:

  • Faster installs: 10-100x faster than pip
  • Dependency resolution: More reliable than pip-tools
  • Tool management: Built-in support for development tools
  • Environment isolation: Better virtual environment handling

Building from Source

โš ๏ธ Use UV for all Python operations as per project standards

# Install required tools using UV
uv tool install maturin
uv tool install patchelf

# Install project dependencies
cd eventuali-python
uv sync

# Build and install in development mode
uv run maturin develop

# Run tests
uv run pytest

# Format code
uv run black ../examples/
uv run ruff check ../examples/ --fix

Testing Your Build

After building, verify everything works by running the examples using UV:

# Test the Rust core (fastest way to verify the build)
cargo run --package eventuali-core --example rust_streaming_demo

# Test Python bindings compilation
cargo build --package eventuali-python

# Run Python examples using UV (required)
cd eventuali-python
uv run python ../examples/01_basic_event_store_simple.py
uv run python ../examples/02_aggregate_lifecycle.py
uv run python ../examples/03_error_handling.py
uv run python ../examples/04_performance_testing.py

# Advanced examples
uv run python ../examples/05_multi_aggregate_simple.py
uv run python ../examples/06_event_versioning.py
uv run python ../examples/07_saga_patterns.py
uv run python ../examples/08_projections.py

See the Examples section for comprehensive documentation on running and understanding each example.

Performance

Benchmarks show significant performance improvements over pure Python event sourcing:

  • Serialization: 20-30x faster
  • Database operations: 2-10x faster
  • Memory usage: 8-20x more efficient
  • Concurrent throughput: 2x better under load

Examples

This section provides comprehensive examples demonstrating Eventuali's capabilities, from basic event sourcing concepts to high-performance streaming.

๐Ÿ“– Quick Example Navigation

๐Ÿ“š Basic Examples (01-04) - Learn the Fundamentals

๐Ÿ”„ Intermediate Examples (05-08) - Production Patterns

๐Ÿš€ Advanced Examples (09-16) - Enterprise Scale

๐Ÿ”ง CLI Examples (17-20) - Production Tooling

๐Ÿ“‹ Complete Examples Documentation โ†’ - Detailed guides, expected outputs, and performance metrics

Prerequisites

Before running examples, ensure you have the required dependencies:

# Install Rust (required for all examples)
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh

# Install Protocol Buffers compiler (for Rust examples)
# Ubuntu/Debian:
sudo apt install protobuf-compiler
# macOS:
brew install protobuf

# Build the project
cargo build --release

# For Python examples, compile Python bindings
cargo build --package eventuali-python

Rust Examples

High-Performance Streaming Demo

Location: eventuali-core/examples/rust_streaming_demo.rs

This comprehensive example demonstrates the full power of Eventuali's Rust core, showcasing real-world event sourcing and streaming scenarios.

# Run the complete streaming demonstration
cargo run --package eventuali-core --example rust_streaming_demo

What it demonstrates:

  • โœ… High-performance event store with SQLite backend
  • โœ… Real-time event streaming with broadcast channels
  • โœ… Projection system building read models from events
  • โœ… Position tracking for reliable exactly-once processing
  • โœ… Event sourcing with full event replay capabilities
  • โœ… Batch processing demonstrating high throughput
  • โœ… Complete async workflow with Tokio

Expected Performance:

  • 10,000+ events/second throughput
  • Real-time streaming with < 1ms latency
  • Memory-efficient processing of large event batches
  • Demonstrates the 10-60x performance improvements over Python

Sample Output:

=== Eventuali Rust Streaming Demo ===

1. Setting up SQLite event store...
   โœ“ Event store ready

2. Creating high-performance event streamer...
   โœ“ Event streamer connected to store

3. Setting up user projection...
   โœ“ Projection subscribed to User events

...

10. Performance demonstration...
   โœ“ Saved 100 events in 9.309ms (10742.08 events/sec)
   โœ“ Projection now contains 103 users

=== Demo completed successfully! ===
Key achievements:
โœ“ High-performance event store with SQLite backend
โœ“ Real-time event streaming with broadcast channels
โœ“ Projection system building read models from events
โœ“ Position tracking for reliable exactly-once processing
โœ“ Event sourcing with full event replay capabilities
โœ“ Batch processing demonstrating high throughput
โœ“ Production-ready Rust implementation complete

Python Examples

Basic Event Sourcing

Location: examples/basic_usage.py

Learn the fundamentals of event sourcing with this comprehensive introduction.

cd eventuali-python
uv run python ../examples/basic_usage.py

What you'll learn:

  • Creating domain events with Pydantic models
  • Building aggregates that apply events
  • Event serialization and deserialization
  • Event replay to reconstruct state
  • State consistency verification

Key Concepts Covered:

  • Domain events (UserRegistered, UserEmailChanged, UserDeactivated)
  • Aggregate root pattern with the User aggregate
  • Business methods that generate and apply events
  • Event sourcing state reconstruction

Advanced Streaming Example

Location: examples/streaming_example.py

Explore real-time event streaming and projection building.

cd eventuali-python  
uv run python ../examples/streaming_example.py

What you'll learn:

  • Setting up event stores with different backends
  • Creating high-performance event streamers
  • Building real-time projections from event streams
  • Event filtering by aggregate and event type
  • Position tracking for reliable processing
  • Integration between EventStore and EventStreamer

Features Demonstrated:

  • Real-time event subscriptions
  • Background event processing
  • Projection-based read models
  • Event type filtering
  • Stream position management

Unit Tests and Testing Patterns

Location: eventuali-python/tests/test_basic.py

Learn how to test event sourcing applications effectively.

cd eventuali-python
uv run pytest tests/test_basic.py -v

Testing Patterns Covered:

  • Event creation and serialization testing
  • Aggregate behavior verification
  • Business method testing
  • Event replay testing
  • Async event store operations (when available)

Running the Examples

Quick Start - Rust Demo

The fastest way to see Eventuali in action:

# Clone and build
git clone git@github.com:primevalai/eventuali.git
cd eventuali
cargo build --release

# Run the high-performance demo
cargo run --package eventuali-core --example rust_streaming_demo

Python Examples Setup

All Python examples use UV for dependency management:

# Setup development environment
cd eventuali/eventuali-python
uv sync
uv tool install maturin
uv tool install patchelf

# Build Python bindings
uv run maturin develop

# Test CLI functionality (now available)
uv run eventuali --help
uv run eventuali config --list
uv run eventuali init --database-url "sqlite://:memory:" --force
uv run eventuali query --limit 5

# Quick start examples (basic)
uv run python ../examples/01_basic_event_store_simple.py     # Basic event sourcing
uv run python ../examples/02_aggregate_lifecycle.py         # Complex aggregates
uv run python ../examples/03_error_handling.py              # Error patterns
uv run python ../examples/04_performance_testing.py         # Performance benchmarks (64k+ events/sec)

# Production patterns (intermediate)
uv run python ../examples/05_multi_aggregate_simple.py      # Multi-aggregate coordination
uv run python ../examples/06_event_versioning.py            # Schema evolution
uv run python ../examples/07_saga_patterns.py               # Distributed transactions (~214ms avg)
uv run python ../examples/08_projections.py                 # Real-time projections (78k+ events/sec)

# Enterprise scale (advanced)
uv run python ../examples/09_cqrs_patterns.py               # CQRS with multiple read models
uv run python ../examples/10_event_replay.py                # Historical state reconstruction
uv run python ../examples/11_distributed_events.py          # Multi-node coordination (100% availability)
uv run python ../examples/12_microservices_integration.py   # 4-service event-driven architecture
uv run python ../examples/13_realtime_dashboards.py         # Live streaming dashboards
uv run python ../examples/14_production_monitoring.py       # Health checks, SLA monitoring (99.9% uptime)
uv run python ../examples/15_advanced_patterns.py           # Snapshots, temporal queries, multi-tenancy
uv run python ../examples/16_enterprise_features.py         # Security, compliance, HA/DR

# CLI tooling examples
uv run python ../examples/17_cli_basic_operations.py        # CLI fundamentals
uv run python ../examples/18_cli_database_management.py     # Database workflows (100% success)
uv run python ../examples/19_cli_performance_monitoring.py  # CLI performance analysis
uv run python ../examples/20_cli_production_workflow.py     # Production deployment pipeline

# Run tests
uv run pytest tests/ -v

# Code quality
uv run black ../examples/
uv run ruff check ../examples/ --fix

Example Progression

We recommend exploring the examples in this order:

  1. Start with Rust Demo - See the full system in action
  2. Basic Python Usage - Learn event sourcing fundamentals
  3. Python Streaming - Understand real-time event processing
  4. Unit Tests - Learn testing patterns

Each example builds on concepts from the previous ones, providing a comprehensive learning path from basic event sourcing to production-ready streaming applications.

Performance Insights from Examples

The Rust streaming demo consistently demonstrates:

  • 10,000+ events/second sustained throughput
  • Sub-millisecond event processing latency
  • Memory efficiency with large event volumes
  • Reliable processing with position tracking
  • Real-time projections with immediate consistency

This showcases the core value proposition: Rust-level performance with Python-level usability.

License

This project is licensed under either of

at your preference.

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

eventuali-0.2.2.tar.gz (5.2 MB view details)

Uploaded Source

File details

Details for the file eventuali-0.2.2.tar.gz.

File metadata

  • Download URL: eventuali-0.2.2.tar.gz
  • Upload date:
  • Size: 5.2 MB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.12.9

File hashes

Hashes for eventuali-0.2.2.tar.gz
Algorithm Hash digest
SHA256 294450cd18f4596b8c2c3d498d9c3cff53a4f97be9ba92607d0fd859bf0826a8
MD5 94e2ec8c9264f43a18263028db6467fb
BLAKE2b-256 45cc3b574469ad20d7db3d063961e2e5f6ce2539087f623897fdebff8888b119

See more details on using hashes here.

Provenance

The following attestation bundles were made for eventuali-0.2.2.tar.gz:

Publisher: publish.yml on primevalai/onyx-octopus

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

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