Quantstrip docs
Open Dashboard

Import surface

from quantstrip import (
    ClientBase,      # base class for your client
    db_handler,      # DBHandler singleton — see the database API
    email_manager,   # EmailManager singleton — see the email API
    settings,        # Settings singleton — see the settings API
    send_email,      # shorthand for email_manager's default-account send
)

Only ClientBase is documented on this page. db_handler, email_manager, settings, and send_email are re-exports — see database, email, and settings for their full method surfaces.

class ClientBase

Base class for every client. Subclass it, do your setup in __init__ (after calling super().__init__()), schedule jobs on self.scheduler (a schedule.Scheduler), and call run_client() to start.

stop_client()

Sets the internal stop flag. The running main_loop thread exits on its next iteration.

start_client()

Resets lifecycle state — clears the stop flag, records the start timestamp, resets job_count and last_job_error, and stamps the initial heartbeat. Called automatically by run_client; you generally don't call this directly.

get_resource_usage()

Returns None if the client hasn't been started yet. Otherwise returns a dict:

cpu_percent · thread_count · last_heartbeat · job_count · last_job_error
run_client(client_id, thread_name="Client - main_loop")

Starts main_loop on a background thread and sets is_running = True. This is what you call from your client's entry point to actually go live.

main_loop()

Runs on the background thread started by run_client. Every 100ms: runs any pending jobs on self.scheduler, increments job_count, and updates the heartbeat. Continues until the stop flag is set.

A single job raising an exception is caught, logged, and recorded in last_job_error — it does not stop the loop. An exception in the loop itself (outside a job) is fatal: it's logged, exception is set to a "FATAL: ..." string, and the client stops.

Minimal example

A client that logs a message once a second — the actual pattern used by the smallest example in the codebase:

from quantstrip import ClientBase
import logging

logger = logging.getLogger(__name__)

class Client(ClientBase):
    def __init__(self, *args):
        super().__init__()
        self.display_name = "Default Client"
        self.scheduler.every(1).seconds.do(self.job)

    def job(self):
        logger.info(f"Hello from {self.display_name}")

# Elsewhere, to go live:
client = Client()
client.run_client(client_id="default-client-1")
See General client template for the full walkthrough of this pattern, and IBKR template for a client that also places orders and writes executions through db_handler.