Files
foxhunt/testing/api-gateway-load/src/clients/mixed_workload.rs
jgrusewski 9c3d741a08 refactor: restructure repo — crates/, bin/, testing/ layout
Move 17 library crates into crates/, CLI binary into bin/fxt,
consolidate 10 test crates into testing/, split config crate
from deployment config files.

Root directory reduced from 38+ to ~17 directories.
All Cargo.toml paths and build.rs proto refs updated.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-25 11:56:00 +01:00

84 lines
2.5 KiB
Rust

use anyhow::Result;
use tokio::sync::mpsc;
use super::authenticated_client::*;
use crate::metrics::RequestMetric;
pub struct MixedWorkloadClient {
client: AuthenticatedClient,
client_id: usize,
metrics_tx: mpsc::UnboundedSender<RequestMetric>,
}
impl MixedWorkloadClient {
pub fn new(
client: AuthenticatedClient,
client_id: usize,
metrics_tx: mpsc::UnboundedSender<RequestMetric>,
) -> Self {
Self {
client,
client_id,
metrics_tx,
}
}
/// Run mixed workload with realistic distribution:
/// - 60% order submissions
///
/// - 30% position queries
/// - 8% backtesting requests
///
/// - 2% ML training requests
pub async fn run_mixed_workload(&mut self, duration: std::time::Duration) -> Result<()> {
use rand::Rng;
let start = std::time::Instant::now();
while start.elapsed() < duration {
// Generate random number each iteration to avoid holding RNG across await
let workload_type = {
let mut rng = rand::thread_rng();
rng.gen_range(0..100)
};
let metric = match workload_type {
0..=59 => {
// 60% - Submit order
self.client
.submit_order(self.client_id, TestOrder::random())
.await?
},
60..=89 => {
// 30% - Query positions
self.client.get_positions(self.client_id).await?
},
90..=97 => {
// 8% - Run backtest
self.client
.run_backtest(self.client_id, BacktestConfig::default())
.await?
},
98..=99 => {
// 2% - Train model
self.client
.train_model(self.client_id, TrainingConfig::default())
.await?
},
_ => unreachable!(),
};
self.metrics_tx.send(metric)?;
// Small random think time (1-50ms) to simulate realistic user behavior
let think_time_ms = {
let mut rng = rand::thread_rng();
rng.gen_range(1..=50)
};
tokio::time::sleep(tokio::time::Duration::from_millis(think_time_ms)).await;
}
Ok(())
}
}