Commit Graph

626 Commits

Author SHA1 Message Date
jgrusewski
4c23f8c50c security(api-gateway): implement X.509 signature verification for mTLS
Replace the TODO stub in validate_certificate_chain with full
cryptographic chain-of-trust verification using x509-parser's ring-backed
verify feature:

1. Issuer CN matching -- client cert issuer must equal CA subject CN
2. CA validity period -- reject expired or not-yet-valid CA certificates
3. CA Basic Constraints -- verify the signer actually has cA=true
4. Cryptographic signature -- verify client cert TBS data signature
   against the CA's SubjectPublicKeyInfo (RSA/ECDSA/Ed25519 via ring)

Also enables the "verify" feature on x509-parser and extends the method
signature to accept ca_cert_pem for proper chain validation.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 19:19:35 +01:00
jgrusewski
2fa459cf08 fix(ml): replace unwrap() with ok_or/? in DQN IQN paths
Replace 6 unwrap() calls with safe error handling in DQN IQN code:
- Production: 3 unwrap() on iqn_network/iqn_target_network replaced with
  ok_or_else returning MLError::ModelError for clear diagnostics
- Tests: 2 result.unwrap() replaced with ?, 2 DQN::new().unwrap() replaced
  with ? after changing test signatures to return anyhow::Result<()>

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 19:12:16 +01:00
jgrusewski
86712a1216 docs: production readiness phase 3 implementation plan — 18 tasks
Bite-sized steps for each task with exact file paths, code snippets,
verification commands, and parallel execution strategy.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 19:00:43 +01:00
jgrusewski
aa6669ede0 docs: production readiness phase 3 design — 18 tasks across 4 pillars
Safety, live trading, security, and observability gaps identified
from comprehensive codebase audit. Organized for parallel swarm execution.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 18:53:38 +01:00
jgrusewski
6cdffda475 fix(ml): silence unsafe-code warnings on inference adapter Send/Sync impls
Add #[allow(unsafe_code)] on each unsafe impl Send/Sync for the four
inference adapters (DQN, PPO, TFT, Mamba2). The SAFETY comments explain
why these are sound — Mutex provides exclusive access.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 18:39:05 +01:00
jgrusewski
06329a3e96 fix(trading_service): replace placeholder VaR with proper historical simulation
Implement real quantile-based VaR at 95% and 99% confidence, proper
Expected Shortfall (CVaR) as tail mean, sqrt-of-time 10-day scaling,
and safe .get() access instead of array indexing.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 18:27:09 +01:00
jgrusewski
434a7653a2 feat(data_acquisition): implement MinIO uploader with object_store
Wire S3-compatible upload/exists/delete using object_store crate.
Fix generate_object_key to return Result instead of panicking.
Add 4 unit tests with InMemory backend.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 18:25:42 +01:00
jgrusewski
abcbf84509 feat(trading_service): wire MLEngine with real EnsembleCoordinator
Replace empty MLEngine struct with actual EnsembleCoordinator from ml
crate. Registers DQN, PPO, TFT, Mamba2 models with configurable
weights loaded from config repository.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 18:24:52 +01:00
jgrusewski
a1ba3ea577 feat: production readiness Phase 1-2 implementation
- fix(trading_engine): replace Prometheus panic! with graceful registration
- fix(trading_service): implement partial fill matching in order book
- feat(trading_service): replace feature extraction stub with real 51-dim pipeline
- feat(trading_service): wire RiskEngine with real VaR calculator
- fix(api_gateway): implement real ML prediction proxy
- feat(data_acquisition): implement DBN data downloader
- feat(data): wire DBN uploader with MinIO integration

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 18:21:45 +01:00
jgrusewski
13186424d9 fix(data): implement real Databento stream poll_next
Replace stub Poll::Pending with actual stream polling that reads from
underlying data source and converts DBN messages to MarketEvents.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 18:17:43 +01:00
jgrusewski
ee1cf23972 Merge branch 'worktree-backtesting-vertical-slice'
Backtesting vertical slice: connect 8 disconnected pipeline layers
so DBN files + trained model checkpoints produce real backtest PnL
with trade-by-trade history.

- DBN ProcessedMessage → MarketEvent converter
- DBN replay engine with mpsc channel streaming
- Production 51-dim feature extractor (replacing 3-5 dim local)
- BacktestMLModel wrapper bridging ensemble adapters → MLModel trait
- Model checkpoint loading and registry startup
- Real PositionTracker accounting (weighted avg, partial fills, flips)
- PnL tracking with equity curve and trade history in finalize()
- End-to-end integration test (54 tests total, 0 failures)
2026-02-21 17:35:15 +01:00
jgrusewski
86b6957353 test(backtesting): add end-to-end DBN backtest integration test
Validates full pipeline: DBN converter roundtrip, replay engine streaming,
model loading + prediction, 51-dim feature extraction, and synthetic
backtest with DQN model producing real predictions.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 16:06:19 +01:00
jgrusewski
4d3140cfab fix(backtesting): wire PnL tracking and trade history in AdaptiveStrategyRunner
PerformanceTracker now records open entries, computes realized PnL on
position close, tracks equity curve snapshots, and populates trades
and performance_timeline in finalize() instead of returning empty vecs.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 16:05:59 +01:00
jgrusewski
b9ead01286 fix(backtesting): implement PositionTracker position accounting and trade recording
Replace stub update_position() and record_trade() with real accounting:
weighted-average entry price, realized PnL on close, partial fills,
position flips (long→short), and trade history recording.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 16:00:07 +01:00
jgrusewski
45eabb71df feat(backtesting): add BacktestMLModel wrapper and registry loader
BacktestMLModel bridges ModelInferenceAdapter → MLModel trait for the
global ModelRegistry. load_models_for_backtest() creates DQN/PPO
adapters from checkpoint files and registers them for inference.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:59:46 +01:00
jgrusewski
b6dfe8e6c4 feat(backtesting): wire production 51-dim feature extractor
Replace local 3-5 feature FeatureExtractor with ProductionFeatureExtractorAdapter
from ml::features. Falls back to legacy extractor during warmup period.
Production extractor produces exactly 51 features matching DQN/PPO training.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:51:02 +01:00
jgrusewski
5891d392e7 feat(backtesting): add DBN replay engine for historical data
DbnReplayEngine loads events and streams them through mpsc channels,
compatible with StrategyTester. Supports from_events() for testing
and from_bytes() stub for DBN file parsing.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:50:43 +01:00
jgrusewski
1a5f0a5202 feat(backtesting): add DBN ProcessedMessage to MarketEvent converter
Converts Trade, Ohlcv, and Quote variants from data::ProcessedMessage
to trading_engine::MarketEvent. Handles HardwareTimestamp→DateTime<Utc>,
Decimal→Quantity, and String→Symbol type conversions.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:48:17 +01:00
jgrusewski
b2f38ea186 chore: add .worktrees/ to .gitignore
Prevent worktree contents from being tracked.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:32:45 +01:00
jgrusewski
58d2d8ddee fix(data): return None for unsupported DBN event types instead of placeholder trades
The catch-all match arm in convert_to_common_event was creating synthetic
TradeEvent objects with symbol "UNKNOWN", price zero, and trade_id "placeholder"
for any MarketDataEvent variant not explicitly handled (Bar, OrderBook, News, etc.).
These fake trades corrupt downstream analytics pipelines. Now returns None and
logs at debug level instead, allowing callers to filter unsupported types cleanly.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:32:02 +01:00
jgrusewski
4069eb473c docs: backtesting vertical slice implementation plan
8-task TDD plan to bridge 8 disconnected layers in the backtesting
pipeline: DBN converter, replay engine, 51-dim feature wiring,
model loader, registry startup, position tracking, PnL tracking,
and end-to-end integration test.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:30:00 +01:00
jgrusewski
4354098d11 docs: Phase 1-2 data pipeline and trading service implementation plan
13-task plan covering data pipeline fixes (Databento stream, data acquisition,
DBN uploader) and trading service core wiring (RiskEngine, MLEngine, VaR,
feature extraction, order matching, API gateway, Prometheus panics).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:25:17 +01:00
jgrusewski
30241e858d docs: backtesting vertical slice production readiness design
8-task plan to bridge disconnected backtesting pipeline layers:
DBN parser → feature extraction → ML inference → position tracking → PnL

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:21:22 +01:00
jgrusewski
e2a712593a docs: full system production readiness design (6-phase plan)
Covers data pipeline, trading service core, broker connectivity
(FIX 4.4 + TWS), execution algorithms, security/compliance, and
observability — based on comprehensive non-ML audit.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:18:19 +01:00
jgrusewski
faa7b85cea docs: real-data ensemble backtest and hyperopt deploy design
Two-phase design:
A) Real 6E.FUT data → 4-model ensemble → PaperBroker → P&L metrics
B) Best hyperopt params → train → deploy to ensemble → ValidationHarness

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 15:04:58 +01:00
jgrusewski
2dd3326aec docs: ensemble real inference design and implementation plan
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 14:58:36 +01:00
jgrusewski
07ab29b8b3 Merge branch 'worktree-full-stack-ml-integration' 2026-02-21 14:56:36 +01:00
jgrusewski
a53daba333 test(paper_trading): add end-to-end pipeline integration test
Replays 100 bars of synthetic price data through:
DQN+PPO ensemble → TradeSignal → PaperBroker → PnLTracker
Verifies finite Sharpe, bounded drawdown, and trade execution.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 14:30:35 +01:00
jgrusewski
ed320c936b feat(paper_trading): add PaperBroker and PnLTracker for simulated trading
PaperBroker: simulated fills with configurable slippage and commission.
PnLTracker: rolling Sharpe ratio (252-day window), max drawdown, cumulative return.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 14:26:00 +01:00
jgrusewski
dc3952ce22 feat(ensemble): add TradeSignal type with Buy/Sell/Hold action mapping
TradeSignal converts ensemble predictions to actionable trade signals:
direction > 0.1 → Buy, < -0.1 → Sell, else Hold.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 14:25:02 +01:00
jgrusewski
b529c0b1db feat(hyperopt): add campaign runner with results persistence
CampaignResults with serde serialization. run_campaign() orchestrates
ArgminOptimizer for DQN hyperopt, saves best_params.json and
campaign_summary.json to timestamped results directory.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 14:16:02 +01:00
jgrusewski
5dddf365e5 feat(hyperopt): add CampaignConfig with DQN/PPO defaults and GPU limits
Campaign configuration for systematic multi-trial optimization:
- DQN: 50 trials, SHA η=3, 81 max epochs
- PPO: 30 trials, Hyperband, 81 max epochs
- Batch size clamped at 230 (RTX 3050 Ti 4GB VRAM)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 14:09:59 +01:00
jgrusewski
9e994dba0c test(ensemble): add 4-model inference ensemble integration test
Constructs DQN, PPO, Mamba2, and TFT adapters with small configs,
pre-warms the sequence-based models, then feeds 5 feature vectors
through InferenceEnsemble and verifies bounded predictions from
all 4 models.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 14:05:49 +01:00
jgrusewski
3bf3a2a0bb feat(ensemble): add InferenceEnsemble coordinator with confidence-weighted aggregation
Lightweight synchronous coordinator that wraps N ModelInferenceAdapter
instances. Aggregates predictions via confidence-weighted voting with
graceful degradation for unready or failing models.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:59:18 +01:00
jgrusewski
be986df748 chore(ml): remove remaining broken integration test files
Additional test files with compilation errors (missing fields, private types,
unresolved imports) that cannot be fixed without major refactoring.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:48:17 +01:00
jgrusewski
89079a72c9 test(ensemble): add checkpoint round-trip and full integration tests
- DQN adapter: save/load/predict round-trip validation
- Coordinator: full ensemble with real DQN adapter integration test

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:42:32 +01:00
jgrusewski
27ada2ff58 fix(ml): fix test files using wrong foxhunt_ml:: crate name
Replaced foxhunt_ml:: with ml:: in 4 test files:
- dqn_full_gradient_flow_integration_test.rs
- dqn_gradient_flow_isolation_test.rs
- tft_int8_forward_integration_test.rs
- tft_int8_integration_test.rs

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:40:25 +01:00
jgrusewski
c300fa0551 feat(ensemble): integrate real inference adapters into coordinator
Replace mock predictions with real model inference when adapters are
registered. Falls back to mock predictions for models without adapters.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:35:28 +01:00
jgrusewski
184ed935e1 chore(ml): delete 88 stale test files referencing removed WorkingDQN type
These test files reference WorkingDQN/WorkingDQNConfig which were removed
from the codebase. They cannot compile and provide no test coverage.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:32:43 +01:00
jgrusewski
c402da4c8b feat(ensemble): add TFT inference adapter with sequence buffering
Implements TftInferenceAdapter that wraps the Temporal Fusion Transformer
for ensemble prediction. Unlike single-step models (DQN, PPO), TFT requires
a sequence of observations before running inference. The adapter maintains
an internal VecDeque buffer that collects sequence_length feature vectors,
then constructs static/historical/future tensors for the TFT forward pass.
Median quantile is mapped to directional signal via smooth saturating
function; IQR provides confidence estimation.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:27:11 +01:00
jgrusewski
919773a741 docs: full-stack ML integration design (cleanup → ensemble → hyperopt → paper trading)
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:19:17 +01:00
jgrusewski
37d617fb6a feat(mamba): add directional MSE loss and fix ZOH->bilinear discretization
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:17:31 +01:00
jgrusewski
93447ec1de feat(ensemble): add DQN and PPO inference adapters
Implement ModelInferenceAdapter for DQN (Q-value argmax -> direction + softmax confidence)
and PPO (probability-weighted action values -> direction + max prob confidence) with
zero-padding for mismatched feature dimensions and 6 passing unit tests.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:13:33 +01:00
jgrusewski
7ecd10e793 Merge branch 'feature/codebase-cleanup' 2026-02-21 13:07:29 +01:00
jgrusewski
20cbe7a7fa feat(ensemble): add ModelInferenceAdapter trait and types
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 13:02:42 +01:00
jgrusewski
c4d0f086f0 test(ml): add production training integration smoke test
Validates all production training pipeline components work together:
- QR-DQN defaults (use_qr_dqn=true, num_quantiles=32, qr_kappa=1.0)
- 42D parameter space dimensionality and round-trip preservation
- SuccessiveHalving early stopping (construction + pruning logic)
- Hyperband early stopping (rung-based vs non-rung pruning)
- ObjectiveMode PartialEq comparison
- QR-DQN training on real 6E.FUT data (5 epochs, finite non-zero loss)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 12:57:55 +01:00
jgrusewski
66c2ff7095 feat(hyperopt): add ObjectiveMode and two-phase optimization orchestration
Add ObjectiveMode enum (EpisodeReward/Sharpe) to DQNTrainer and a
TwoPhaseObjective trait + optimize_two_phase() method to ArgminOptimizer.
Phase A optimizes episode reward for fast convergence, Phase B (pending
model Clone support) refines with Sharpe ratio. This keeps the static
extract_objective trait method untouched by separating objective switching
into instance-level state.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 12:50:17 +01:00
jgrusewski
689231d6cb feat(data): integrate MBP10/OFI features into training data pipeline
Add load_ofi_features() helper to both DQN and PPO trainer adapters
that loads MBP10 snapshots from a sibling mbp10/ directory, computes
8-slot OFI feature vectors via OFICalculator, and overlays them onto
positions 43-50 of the training feature arrays. Gracefully falls back
to zero-padded features when MBP10 data is not available.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 12:40:41 +01:00
jgrusewski
11d486021f feat(dqn): wire QR-DQN QuantileNetwork through hyperopt to training loop
Add use_qr_dqn, num_quantiles, qr_kappa fields to DQNHyperparameters
and pass them from DQNParams (hyperopt) through to DQNConfig (agent),
replacing hardcoded IQN values in the trainer.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 12:33:21 +01:00
jgrusewski
e29b6ac307 feat(hyperopt): add QR-DQN parameters to DQN hyperopt search space (40D->42D)
Add num_quantiles and qr_kappa to the continuous search space for
Quantile Regression DQN, replacing the disabled C51 distributional RL
(BUG #36). QR-DQN is enabled by default with 32 quantiles and kappa=1.0.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-21 12:26:38 +01:00