Skip to main content

A flexible, event-driven, multi-agent framework for building algorithmic trading strategies using the Alpaca API.

Project description

Trading Algo Framework

A flexible, event-driven, multi-agent framework for building algorithmic trading strategies using the Alpaca API.

Key Features

  • Multi-Agent Architecture: Build your strategy by combining independent, reusable agents.
  • Event-Driven: Agents communicate through an event bus, reacting to market data or other internal events.
  • Hybrid Agent Support: Supports both event-driven agents (reacting to market data) and periodic agents (running on a schedule).
  • Extensible: Easily create your own custom agents to encapsulate specific logic.
  • Alpaca Integration: Connects to Alpaca for market data streams and trade execution.
  • Live Performance Tracking: Includes a built-in agent for live PnL tracking with graphical visualization.

Core Concepts

  • Trading Hub: The central engine that manages the lifecycle of agents, and orchestrates the flow of data.
  • EventDrivenAgent: A base class for agents that react to market data events. The frequency of execution is controlled by a throttle.
  • PeriodicAgent: A base class for agents that run on a fixed schedule. The execution frequency is controlled by a period.
  • Communication Bus: A publish-subscribe system that allows agents to communicate with each other in a decoupled manner. Agents can publish events and subscribe to listen to events from other agents.
  • DataObject: A standardized container for data flowing through the communication bus.

Installation

You can install the trading-algo package directly from PyPI:

pip install trading-algo

Prerequisites

  • Python 3 3.9+

Configuration

This framework requires Alpaca API keys to connect to the market. You can provide these in two ways:

  1. Environment Variables (Recommended for Production): Set APCA_API_KEY_ID and APCA_API_SECRET_KEY in your environment. The TradingHub will automatically pick these up if no keys are explicitly provided.

  2. Directly to TradingHub (Recommended for Examples/Development): You can pass your API key and secret directly when initializing the TradingHub:

    from trading_algo import TradingHub
    trading_hub = TradingHub(api_key="YOUR_API_KEY", secret_key="YOUR_SECRET_KEY", paper=True)
    

    For examples, you might read these from a local config.ini file (as shown in the examples) or other local configuration.

Usage

The main entry point for a strategy is a script where you instantiate a TradingHub, add your desired agents, and start the hub.

Here's an example demonstrating a simple multi-agent strategy:

# examples/multi_agent_strategy.py

import asyncio
import os
import configparser
from loguru import logger

from trading_algo import TradingHub, Spotter, SpreadCalculator, DeltaHedger, Quoter, PerformanceTrackerAgent

async def main():
    """Main function to set up and run the algorithm."""
    logger.remove()
    logger.add("multi_agent_strategy.log", rotation="5 MB", level="DEBUG", catch=False)
    logger.add(sys.stderr, level="INFO")
    logger.info("Setting up the TradingHub and its agents.")

    # --- API Key Configuration ---
    # For examples, we'll try to read from config.ini first, then environment variables.
    # In a production setup, environment variables are recommended.
    api_key = os.getenv("APCA_API_KEY_ID")
    secret_key = os.getenv("APCA_API_SECRET_KEY")
    paper_trading = True # Set to False for live trading

    if not api_key or not secret_key:
        config = configparser.ConfigParser()
        config_path = os.path.join(os.path.dirname(__file__), '..', 'config.ini')
        if os.path.exists(config_path):
            config.read(config_path)
            try:
                api_key = config['alpaca']['api_key']
                secret_key = config['alpaca']['secret_key']
                logger.info("Alpaca API keys loaded from config.ini")
            except KeyError:
                logger.warning("API keys not found in config.ini. Please ensure [alpaca] section with api_key and secret_key exists.")
        else:
            logger.warning("config.ini not found. Attempting to use environment variables.")

    if not api_key or not secret_key:
        logger.error("Alpaca API keys not found in config.ini or environment variables (APCA_API_KEY_ID, APCA_API_SECRET_KEY). Please provide them.")
        return

    # 1. Initialize the core components
    trading_hub = TradingHub(api_key=api_key, secret_key=secret_key, paper=paper_trading)

    # 2. Define the instruments to trade
    instruments = ["AAPL", "MSFT"]

    # 3. Instantiate and add agents to the hub
    await trading_hub.add_agent(Spotter, {'instruments': instruments, 'throttle': '5s'})
    await trading_hub.add_agent(SpreadCalculator, {'instruments': instruments, 'throttle': '200ms'})
    await trading_hub.add_agent(DeltaHedger, {'period': '30s'})
    await trading_hub.add_agent(Quoter, {'instruments': instruments, 'period': '5s'})
    await trading_hub.add_agent(PerformanceTrackerAgent, {'period': '30s'}) # Added performance tracker

    # 4. Start the hub. This will run until interrupted.
    await trading_hub.start()


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

To run the example strategy, execute the following command from the project root:

python examples/multi_agent_strategy.py

Creating a Custom Agent

You can easily create your own agents by inheriting from EventDrivenAgent or PeriodicAgent. The example below shows a simple PeriodicAgent that calculates and publishes a quote.

from trading_algo import PeriodicAgent, DataObject

class MyCustomQuoter(PeriodicAgent): # Renamed class to avoid conflict with example
    """
    A simple periodic agent that calculates and publishes quotes.
    """
    def __init__(self, config, data_cache, communication_bus):
        # Pass a 'period' for periodic execution
        super().__init__(config, data_cache, communication_bus, period='5s')
        self.last_spot_price = None

    async def initialize(self):
        # Subscribe to spot price events from other agents
        await self.communication_bus.subscribe_listener(
            "SPOT_PRICE('AAPL')",
            self.on_spot_price
        )

    async def on_spot_price(self, spot_price: DataObject):
        # Store the latest spot price
        self.last_spot_price = spot_price.get('value')

    async def run(self):
        # Core logic for the periodic agent
        if self.last_spot_price:
            # Calculate bid/ask
            bid_price = self.last_spot_price * 0.99
            ask_price = self.last_spot_price * 1.01
            
            # Publish the new quote on the communication bus
            quote_data = DataObject.create('quote', bid=bid_price, ask=ask_price)
            await self.communication_bus.publish("QUOTE('AAPL')", value=quote_data)
            print(f"Published quote for AAPL: Bid={bid_price:.2f}, Ask={ask_price:.2f}")

To use this agent, you would add it to the TradingHub in your main script:

await trading_hub.add_agent(MyCustomQuoter, {'period': '5s'})

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

trading_algo-0.1.3.tar.gz (18.6 kB view details)

Uploaded Source

Built Distribution

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

trading_algo-0.1.3-py3-none-any.whl (20.5 kB view details)

Uploaded Python 3

File details

Details for the file trading_algo-0.1.3.tar.gz.

File metadata

  • Download URL: trading_algo-0.1.3.tar.gz
  • Upload date:
  • Size: 18.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.5

File hashes

Hashes for trading_algo-0.1.3.tar.gz
Algorithm Hash digest
SHA256 61de11c9ebb63f644af3b047b79c303d0c79706b6fed7fa5d5ee402c3b7d5605
MD5 15a5509765d760b75dc43875caaa2357
BLAKE2b-256 a56433787e6c9781b94529b59dca1770992857a03abe39676ab184fe195b9178

See more details on using hashes here.

File details

Details for the file trading_algo-0.1.3-py3-none-any.whl.

File metadata

  • Download URL: trading_algo-0.1.3-py3-none-any.whl
  • Upload date:
  • Size: 20.5 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.5

File hashes

Hashes for trading_algo-0.1.3-py3-none-any.whl
Algorithm Hash digest
SHA256 f142ebfd03eab6efb175c2597bdc8cfaa8a11cc0c452535e1320fce49bfb443e
MD5 5068fe1e5b9ee28d0d18fafba1995b78
BLAKE2b-256 27ef799cb3f30a53949a03b33bac1c04a01bcfec8873bcd9908d5c4561186755

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