Skip to main content

Message bus integration for HAI

Project description

H Message Bus

A message bus integration for HAI applications based on NATS.io

Overview

H Message Bus provides a robust, asynchronous messaging infrastructure built on NATS.io for HAI applications. It enables seamless communication between components through a publish-subscribe pattern, supporting both fire-and-forget messaging and request-response patterns.

Features

  • Asynchronous Communication: Built for modern, non-blocking I/O operations
  • Flexible Message Routing: Publish and subscribe to specific topics
  • High Reliability: Automatic reconnection handling and configurable timeouts
  • Simple API: Focus on core messaging functionality with minimal dependencies

Installation

pip install h_message_bus

Requirements

  • Python 3.10+
  • NATS.io server (can be run via Docker)

Topics

H Message Bus uses topic strings for message routing. It's recommended to follow the convention: hai.[source].[destination].[action]

Example topics:

Topic String Description
hai.ai.tg.chat.send AI sending message to Telegram chat
hai.ai.vectors.save AI saving data to vector database
hai.ai.vectors.query AI querying vector database
hai.tg.ai.chat.send Telegram sending message to AI

You can use these example topics or create your own topic strings based on your application's needs.

Quick Start

Start a NATS Server

The easiest way to get started is with Docker:

docker-compose up -d

Create a Publisher

import asyncio
import uuid
from h_message_bus import NatsConfig, NatsPublisherAdapter, HaiMessage, NatsClientRepository

async def main():
    # Configure NATS connection
    config = NatsConfig(server="nats://localhost:4222")

    # Create NATS client repository
    client_repository = NatsClientRepository(config)

    # Create publisher adapter
    publisher = NatsPublisherAdapter(client_repository)

    # Connect to NATS
    await client_repository.connect()

    # Create and publish a message
    message = HaiMessage(
        id=str(uuid.uuid4()),
        topic="hai.tg.ai.chat.send",
        payload={"text": "Hello AI, this is a message from Telegram", "chat_id": 12345}
    )

    # Publish message
    await publisher.publish(message)

    # Clean up
    await publisher.close()

if __name__ == "__main__":
    asyncio.run(main())

Create a Subscriber

import asyncio
from h_message_bus import NatsConfig, NatsSubscriberAdapter, HaiMessage, NatsClientRepository, MessageProcessor

class MyMessageProcessor(MessageProcessor):
    async def process(self, message: HaiMessage):
        print(f"Received message: {message.id}")
        print(f"Topic: {message.topic}")
        print(f"Payload: {message.payload}")
        print(f"Timestamp: {message.timestamp}")

async def main():
    # Configure NATS connection
    config = NatsConfig(server="nats://localhost:4222")

    # Create NATS client repository
    client_repository = NatsClientRepository(config)

    # Create subscriber
    subscriber = NatsSubscriberAdapter(client_repository)

    # Connect to NATS
    await client_repository.connect()

    # Create message processor
    processor = MyMessageProcessor()

    # Subscribe to a topic
    await subscriber.subscribe("hai.tg.ai.chat.send", processor)

    # Keep the application running
    try:
        print("Subscriber running. Press Ctrl+C to exit.")
        while True:
            await asyncio.sleep(1)
    except KeyboardInterrupt:
        # Clean up
        await client_repository.close()

if __name__ == "__main__":
    asyncio.run(main())

Advanced Usage

Request-Response Pattern

import asyncio
import uuid
from h_message_bus import NatsConfig, NatsPublisherAdapter, HaiMessage, NatsClientRepository

async def main():
    # Configure NATS connection
    config = NatsConfig(server="nats://localhost:4222")

    # Create NATS client repository
    client_repository = NatsClientRepository(config)

    # Create publisher adapter
    publisher = NatsPublisherAdapter(client_repository)

    # Connect to NATS
    await client_repository.connect()

    request_message = HaiMessage(
        id=str(uuid.uuid4()),
        topic="hai.ai.vectors.query",
        payload={"query": "find similar documents", "limit": 10}
    )

    # Send request and wait for response (with timeout)
    response = await publisher.request(request_message, timeout=5.0)

    if response:
        print(f"Received response: {response.payload}")
    else:
        print("Request timed out")

    # Clean up
    await client_repository.close()

if __name__ == "__main__":
    asyncio.run(main())

Creating a Service for Request-Response

import asyncio
import uuid
import json
from h_message_bus import NatsConfig, NatsSubscriberAdapter, NatsPublisherAdapter, HaiMessage, NatsClientRepository, MessageProcessor

class RequestResponseProcessor(MessageProcessor):
    def __init__(self, publisher):
        self.publisher = publisher

    async def process(self, request: HaiMessage):
        print(f"Received request: {request.id}")
        print(f"Payload: {request.payload}")

        # Process the request
        result = {"status": "success", "data": {"result": 42}}

        # Create a response message
        response = HaiMessage(
            id=str(uuid.uuid4()),
            topic=f"{request.topic}.response",
            payload=result
        )

        # Publish the response
        await self.publisher.publish(response)

async def main():
    # Configure NATS connection
    config = NatsConfig(server="nats://localhost:4222")

    # Create NATS client repository
    client_repository = NatsClientRepository(config)

    # Connect to NATS
    await client_repository.connect()

    # Create publisher and subscriber
    publisher = NatsPublisherAdapter(client_repository)
    subscriber = NatsSubscriberAdapter(client_repository)

    # Create request processor that uses the publisher
    processor = RequestResponseProcessor(publisher)

    # Subscribe to the request topic
    await subscriber.subscribe("hai.ai.vectors.query", processor)

    # Keep the application running
    try:
        print("Service running. Press Ctrl+C to exit.")
        while True:
            await asyncio.sleep(1)
    except KeyboardInterrupt:
        # Clean up
        await client_repository.close()

if __name__ == "__main__":
    asyncio.run(main())

Configuration Options

The NatsConfig class allows you to customize your NATS connection:

Parameter Description Default
server NATS server address Required
max_reconnect_attempts Maximum reconnection attempts 10
reconnect_time_wait Time between reconnection attempts (seconds) 2
connection_timeout Connection timeout (seconds) 2
ping_interval Interval for ping frames (seconds) 20
max_outstanding_pings Maximum unanswered pings before disconnect 5

API Reference

Exported Classes

The following classes are exported directly from the package:

  • NatsConfig - Configuration for the NATS connection
  • HaiMessage - Message structure for HAI communication
  • NatsPublisherAdapter - Adapter for publishing messages
  • NatsSubscriberAdapter - Adapter for subscribing to messages
  • MessageProcessor - Processing incoming messages
  • NatsClientRepository - Low-level NATS client operations

HaiMessage Structure

The HaiMessage class is the core data structure used for all messaging:

class HaiMessage:
    id: str               # Unique identifier for the message
    topic: str            # The topic or channel for the message
    payload: dict         # Actual message data
    timestamp: str = None # Optional message creation timestamp (ISO format)

Contributing

Contributions are welcome! Please feel free to submit a Pull Request.

License

This project is licensed under the MIT License - see the LICENSE file for details.

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

h_message_bus-0.0.41.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.

h_message_bus-0.0.41-py3-none-any.whl (12.4 kB view details)

Uploaded Python 3

File details

Details for the file h_message_bus-0.0.41.tar.gz.

File metadata

  • Download URL: h_message_bus-0.0.41.tar.gz
  • Upload date:
  • Size: 11.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.10.11

File hashes

Hashes for h_message_bus-0.0.41.tar.gz
Algorithm Hash digest
SHA256 29f58ba5be9ab1f5763468801a6f9b36aed63402135c9c7e1b31260a1a7c912d
MD5 052a562669a14e1308e5275b132ed777
BLAKE2b-256 27988e503701e8d97ebb7e3ee59b9fdce8ea77c273c4f0c5207c27cc28d7e453

See more details on using hashes here.

File details

Details for the file h_message_bus-0.0.41-py3-none-any.whl.

File metadata

  • Download URL: h_message_bus-0.0.41-py3-none-any.whl
  • Upload date:
  • Size: 12.4 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.10.11

File hashes

Hashes for h_message_bus-0.0.41-py3-none-any.whl
Algorithm Hash digest
SHA256 3846daef1f5d39bcae35b858383fc6105b2d19a65e2b4dc0b086b8da42d81580
MD5 8df81d4d470923ba1b4684718d94abd4
BLAKE2b-256 e2691f1b35cf50ea7d0358e391e8750f886517de0994d83f919783db2da0f767

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