Skip to main content

Repository layout

trading/
  bot.py                Main trading loop β€” all execution logic
  logger.py             Structured logging helpers
  supabase.py           Supabase write helpers
  telegram_commands.py  Telegram command handler

ml/
  feature_engineering.py   59 features + ATR-aware labeling
  ensemble_trainer.py      RF + XGB + LGB signal model training
  ensemble_predictor.py    Signal model inference (majority vote)
  position_trainer.py      Position model training (EXIT/HOLD/ADD)
  position_predictor.py    Position model inference
  sltp_trainer.py          Dynamic SL/TP LightGBM training
  sltp_predictor.py        Dynamic SL/TP inference
  risk_trainer.py          Risk multiplier LightGBM training
  risk_predictor.py        Risk inference: equity-state β†’ [0.10, 1.25]
  model_trainer.py         Shared training utilities + ONNX export
  model_predictor.py       Shared inference base class
  data_preparation.py      Dataset loading + IS/OOS split
  calibration_check.py     Model calibration diagnostics
  news_features.py         News event feature computation
  shap_analysis.py         SHAP feature importance analysis
  hf_hub.py                Hugging Face Hub push / pull / tag
  tune/
    hyperparams.py         Optuna signal model tuning
    position.py            Optuna position model tuning

backtest/
  run.py                 Config-faithful bar-by-bar backtester

scripts/
  onboarding.py          First-time setup wizard
  weekly_optimize.py     Autonomous 13-phase weekly pipeline
  retrain.py             Standalone retrain script
  sweep.py               Config parameter sweep
  sweep_signal.py        Signal-focused sweep
  sweep_pos_model.py     Position model sweep
  optimize_loop.py       Continuous optimization loop
  performance_monitor.py Performance regression detector
  dashboard.py           Terminal dashboard
  compare_configs.py     Compare two config.json files
  config_sync.py         Sync config across machines
  notify.py              Send manual Telegram notification
  run_agent.sh           Launch a Claude Code agent

models/
  model_compat.json      Feature hash + model paths β€” compatibility gate
  risk_metadata.json     Risk model metadata

config/
  brokers.json           Broker registry (symbol, spread, leverage, pip_value)

config.json              Runtime config (active broker, risk, SL/TP, filters)
ml_config.json           ML config (59 features, model paths, labeling params)
trading.py               Entry point β€” calls trading/bot.py
train_ml_model.py        Entry point β€” orchestrates all 4 model trains
backtest.py              Entry point β€” calls backtest/run.py

The three-file rule

Any ML feature change touches exactly three files:
  1. ml/feature_engineering.py β€” add the feature computation
  2. ml_config.json β†’ features array β€” add the name in the correct position
  3. Retrain all 4 models β€” Signal, Position, SLTP, Risk (in that order)
Changing any one without the others breaks inference. The models/model_compat.json file stores a hash of the feature list. On startup, EnsemblePredictor verifies the hash against the current ml_config.json. A mismatch raises ModelCompatibilityError immediately.

Strict training order

Models must always be trained in this order:
Signal β†’ Position β†’ SLTP β†’ Risk
ModelDepends on
SignalNothing (first)
PositionSignal model paths (saved to disk)
SLTPSignal + position models (saved to disk)
RiskCompleted backtest using SLTP models
Training out of order produces either import errors or silent data contamination in the Risk model’s training labels.

Backtester / live parity

backtest/run.py must always mirror trading/bot.py. Every change to execution logic in the bot must be reflected in the backtester, and vice versa. Key parity invariants:
  • Same feature engineering (ml/feature_engineering.py)
  • Same model inference chain (calibrated pkl β†’ ONNX β†’ raw pkl)
  • Same position sizing formula
  • Same equity-aware SL cap
  • Same circuit breakers and gates
  • Same position model evaluation timing
If these diverge, backtest scores become unreliable as live performance predictors.

Lane discipline

The codebase has two clearly separated lanes:
LaneWhoWhat
Client/user laneTrader on their machinePull approved models, run trading.py
Developer laneDeveloper on their machineRetrain, optimize, validate OOS, publish to HF Hub
Clients should never retrain. The live trading host should stay simple β€” it does not need a GPU or the full ML dependency stack (just pip install -r requirements.txt is fine).

Config files

Two config files govern all behavior:
FileWhat it controlsTracked in git
config.jsonRuntime params: symbol, risk, SL/TP, profile, filters, brokerYes
ml_config.jsonFeatures, model paths, labeling, training paramsYes
Both are committed to git. When weekly_optimize.py updates config.json, the change appears in git history. This makes every optimization run fully auditable.

Multi-agent orchestration

For complex tasks, the codebase supports Claude Code agent orchestration:
TASK="run backtest and report score" ./scripts/run_agent.sh
Agent roles:
  • Model Optimizer β€” assesses complexity, writes scope lock, prescribes model tier
  • Project Manager β€” spawns worker agents within the scope lock
  • Feature Engineer β€” validates feature changes, tests OOS impact
  • NOVOSKY Optimizer β€” runs the full SHAP β†’ Optuna β†’ retrain β†’ OOS loop
See Contributing for how to use agents effectively.