Welcome to BetaTrader, a project and a C++ blueprint that explores how a small, exchange-like FX trading engine is put together.
This repository is a deliberate, step-by-step engineering exercise. It contains an in-memory matching core, a compact persistence layer, shared types, logging utilities, and a comprehensive suite of unit tests. The goal is to learn by building: the system is being constructed incrementally, one piece at a time.
This project is for developers, engineers, and curious traders who want a readable, runnable codebase to study matching semantics, order lifecycle, risk checks, and modern C++ development practices.
Status: The common, exchange suite (matching, persistence, fix gateway), and client_fix modules are all implemented and rigorously covered by unit tests. The system features a robust lock-free matching core, a decoupled asynchronous SQLite persistence layer, a functional FIX gateway with thread-safe CompID-based session management and persistent sequence numbers, and a working Dear ImGui client application with an embedded local exchange.
- Learn by Building: Provide a practical, open-source example of a trading system's core components.
- Readability and Simplicity: Prioritize clear, modern C++ code over premature optimization or overly complex designs.
- Test-Driven Development: Emphasize a strong testing culture with extensive unit tests for core logic.
- Extensibility: Design a modular architecture that allows for future expansion with new features, such as different gateways or persistence backends.
| Module | Description | Key Components |
|---|---|---|
common/ |
Shared data structures, types, and utilities used across the project. | Order, Trade, Instrument, Logger, Runbook |
exchange/ |
The core trading engine suite (Modular). | exchange_app, exchange_matching, exchange_fix, exchange_persistence |
client/ |
Frontend suite including a Trader UI and a Load Simulator. | client_fix, client_ui, client_admin, client_app, client_simulator |
vendor/ |
Third-party libraries used for testing, logging, data storage, and UI. | googletest, spdlog, SPSCQueue, SQLiteCpp, GLFW, ImGui, ImPlot |
BetaTrader/
├── CMakeLists.txt
├── CMakePresets.json # Build & Coverage Presets
├── README.md
├── client/ # Frontend UI & Simulator
├── common/ # Shared types & logging
├── exchange/ # Modular Exchange Backend
│ ├── exchange_app/ # Orchestration
│ ├── exchange_fix/ # FIX Gateway
│ ├── exchange_matching/ # Matching Engine
│ ├── exchange_persistence/ # Persistence layer
│ └── ...
├── tools/ # Helper tools (coverage_reporter.py)
└── vendor/ # Bundled third-party libs
These steps will build the project and run all unit tests.
mkdir -p build && cd build
cmake -DCMAKE_BUILD_TYPE=Debug ..
cmake --build . -j$(nproc)
ctest --output-on-failure# Using CMake Presets
cmake --preset coverage
cmake --build build/coverage -j$(nproc)
# Generate and run coverage report
cd build/coverage && make coverage
# View summary
python3 ../../tools/coverage_reporter.py- Build and run the unit tests as described above.
- Explore the tests:
FixEndToEndTests.cpp: Shows the full FIX lifecycle (Logon, Order, MD, Logout).TradingCoreTests.cpp: Detailed tests for engine-level partitioning and command processing.MatcherTests.cpp: Price-time priority matching logic details.AuthRepositoryTests.cpp: Verification of database-backed client authentication.
BetaTrader is divided into several high-level components. Each component contains its own overview and technical specification:
- Exchange Overview: Central hub for the modular exchange backend.
- Matching & Logic: High-performance orderbook and matcher details.
- Data Persistence: Asynchronous SQLite repository details.
- FIX Gateway Overview: Networking and session management details.
- FIX Protocol Reference Guide: Quick reference for tag-value pairs.
- Client Overview: Trader terminal and simulator details.
This repository models a small, exchange-like matching engine. Here are the key concepts implemented:
- Instruments: A simple
enumof currency pairs is defined incommon/include/common/Instrument.h(e.g.,EURUSD,USDJPY). - Order Types:
LimitandMarketorders are supported (common/include/common/Types.h). - Matching Algorithm: The matching engine uses a standard price-time priority algorithm. The execution price is the price of the resting order on the book.
- Fills: Partial fills are supported. Each fill generates a
common::Tradeobject, which is then published and persisted. - Execution Monitoring: Real-time trade executions and order rejections are formatted and dumped directly to standard output, making it easy to track engine activity.
To experiment with trading logic, you can:
- Write a new unit test in
TradingSystemTests.cpp. - Create
common::Orderobjects and wrap them inNewOrdercommands. - Push the commands into a
Partitionand use the mockExecutionPublisherto inspect the resulting trades and order statuses.
This project is a continuous engineering exercise. With the solid foundation of a functional matching core, asynchronous persistence, and a robust FIX gateway now established, here are the most logical next steps for future expansion:
Develop a standalone client application (client) that provides a high-performance Trader UI (using ImGui) and a headless Load Simulator. The Dear ImGui client application (client_app) with embedded local exchange control (client_admin) and FIX session management (ConnectionPanel) is now functional. Remaining work includes the orderbook visualization, trade blotter, portfolio tracker, and the headless load simulator.
While FIX is ideal for high-performance institutional trading, REST and WebSockets are the standard for retail platforms and web UIs. Building a secondary HTTP/WS gateway alongside the FixServer that translates JSON requests into trading_core::Command objects would instantly open the door to building a frontend interface (like React).
An exchange is more dynamic with an active order book. Building a background service or a mock liquidity provider that connects to the engine and continuously publishes random or historically-replayed limit orders and market data updates would populate the books and simulate a live market environment.
Currently, the RiskManager is a foundation awaiting extension. Implementing real pre-trade risk checks such as tracking a client's net open positions, calculating available margin, or implementing "fat finger" checks (e.g., rejecting orders drastically away from the last traded price) would significantly mature the system.
If you plan to contribute to any of these areas, please ensure all unit tests pass and consider updating the relevant .md documentation files.
This project is licensed under the GPL-3.0 License. See the LICENSE file for details.