-
Notifications
You must be signed in to change notification settings - Fork 12
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
052a6df
commit 9a5ecce
Showing
6 changed files
with
153 additions
and
44 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,33 +1,75 @@ | ||
use crate::config::GatlingConfig; | ||
use color_eyre::eyre::Result; | ||
use log::{debug, info}; | ||
use log::info; | ||
use starknet::{core::types::FieldElement, providers::Provider}; | ||
|
||
use starknet::providers::{jsonrpc::HttpTransport, JsonRpcClient}; | ||
use url::Url; | ||
|
||
/// Shoot the load test simulation. | ||
pub async fn shoot(config: &GatlingConfig) -> Result<()> { | ||
pub async fn shoot(config: GatlingConfig) -> Result<SimulationReport> { | ||
info!("starting simulation with config: {:?}", config); | ||
let mut shooter = GatlingShooter::new(config)?; | ||
let mut simulation_report = Default::default(); | ||
// Trigger the setup phase. | ||
setup().await?; | ||
shooter.setup(&mut simulation_report).await?; | ||
// Run the simulation. | ||
run().await?; | ||
shooter.run(&mut simulation_report).await?; | ||
// Trigger the teardown phase. | ||
teardown().await?; | ||
Ok(()) | ||
shooter.teardown(&mut simulation_report).await?; | ||
Ok(simulation_report.clone()) | ||
} | ||
|
||
pub struct GatlingShooter { | ||
config: GatlingConfig, | ||
starknet_rpc: JsonRpcClient<HttpTransport>, | ||
} | ||
|
||
/// Setup the simulation. | ||
pub async fn setup() -> Result<()> { | ||
debug!("setting up!"); | ||
Ok(()) | ||
impl GatlingShooter { | ||
pub fn new(config: GatlingConfig) -> Result<Self> { | ||
let starknet_rpc = starknet_rpc_provider(Url::parse(&config.rpc.url)?); | ||
Ok(Self { | ||
config, | ||
starknet_rpc, | ||
}) | ||
} | ||
|
||
/// Setup the simulation. | ||
async fn setup<'a>(&mut self, _simulation_report: &'a mut SimulationReport) -> Result<()> { | ||
info!("setting up!"); | ||
let chain_id = self.starknet_rpc.chain_id().await?; | ||
info!("chain id: {}", chain_id); | ||
let block_number = self.starknet_rpc.block_number().await?; | ||
info!("block number: {}", block_number); | ||
Ok(()) | ||
} | ||
|
||
/// Teardown the simulation. | ||
async fn teardown<'a>(&mut self, _simulation_report: &'a mut SimulationReport) -> Result<()> { | ||
info!("tearing down!"); | ||
Ok(()) | ||
} | ||
|
||
/// Run the simulation. | ||
async fn run<'a>(&mut self, _simulation_report: &'a mut SimulationReport) -> Result<()> { | ||
info!("firing!"); | ||
let _fail_fast = self.config.simulation.fail_fast.unwrap_or(true); | ||
Ok(()) | ||
} | ||
} | ||
|
||
/// Teardown the simulation. | ||
pub async fn teardown() -> Result<()> { | ||
debug!("tearing down!"); | ||
Ok(()) | ||
/// The simulation report. | ||
#[derive(Debug, Default, Clone)] | ||
pub struct SimulationReport { | ||
pub chain_id: Option<FieldElement>, | ||
pub block_number: Option<u64>, | ||
} | ||
|
||
/// Run the simulation. | ||
pub async fn run() -> Result<()> { | ||
debug!("firing!"); | ||
Ok(()) | ||
/// Create a StarkNet RPC provider from a URL. | ||
/// # Arguments | ||
/// * `rpc` - The URL of the StarkNet RPC provider. | ||
/// # Returns | ||
/// A StarkNet RPC provider. | ||
fn starknet_rpc_provider(rpc: Url) -> JsonRpcClient<HttpTransport> { | ||
JsonRpcClient::new(HttpTransport::new(rpc)) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,20 +1,37 @@ | ||
//! Defines the CLI commands. | ||
|
||
// Imports | ||
use clap::{Parser, Subcommand}; | ||
use clap::{Args, Parser, Subcommand}; | ||
|
||
const VERSION_STRING: &str = concat!(env!("CARGO_PKG_VERSION")); | ||
|
||
/// Main CLI struct | ||
#[derive(Parser, Debug)] | ||
#[command(author, version, about, long_about = None)] | ||
#[command( | ||
author, | ||
version = VERSION_STRING, | ||
about, | ||
long_about = "Gomu Gomu no Gatling is a load testing tool for Starknet RPC endpoints." | ||
)] | ||
pub struct Cli { | ||
#[clap(flatten)] | ||
pub global_opts: GlobalOpts, | ||
|
||
/// The subcommand to run. | ||
#[command(subcommand)] | ||
pub command: Option<Commands>, | ||
pub command: Command, | ||
} | ||
|
||
/// Subcommands | ||
#[derive(Subcommand, Debug)] | ||
pub enum Commands { | ||
pub enum Command { | ||
/// Trigger a load test. | ||
Shoot {}, | ||
} | ||
|
||
#[derive(Debug, Args)] | ||
pub struct GlobalOpts { | ||
/// Configuration file path, optional. | ||
#[clap(short, long, global = true)] | ||
pub config_path: Option<String>, | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,42 +1,56 @@ | ||
//! General configuration | ||
|
||
use color_eyre::eyre::Result; | ||
use config::{Config, File}; | ||
use config::{builder::DefaultState, Config, ConfigBuilder, File}; | ||
use serde_derive::Deserialize; | ||
|
||
/// Configuration for the application. | ||
#[derive(Debug, Deserialize)] | ||
pub struct GatlingConfig { | ||
/// The RPC configuration. | ||
_rpc: Rpc, | ||
pub rpc: Rpc, | ||
/// The simulation configuration. | ||
_simulation: Simulation, | ||
pub simulation: Simulation, | ||
} | ||
|
||
#[derive(Debug, Deserialize)] | ||
#[allow(unused)] | ||
struct Rpc { | ||
pub struct Rpc { | ||
pub url: String, | ||
} | ||
|
||
#[derive(Debug, Deserialize)] | ||
#[allow(unused)] | ||
struct Simulation { | ||
pub struct Simulation { | ||
pub fail_fast: Option<bool>, | ||
} | ||
|
||
impl GatlingConfig { | ||
/// Create a new configuration from environment variables. | ||
pub fn new() -> Result<Self> { | ||
Config::builder() | ||
// Start off by merging in the "default" configuration file | ||
.add_source(File::with_name("config/default")) | ||
// Add in settings from the environment (with a prefix of GATLING) | ||
// Eg.. `GATLING_FAIL_FAST=1 ./target/app` would set the `fail_fast` key | ||
.add_source(config::Environment::with_prefix("gatling")) | ||
base_config_builder() | ||
.build() | ||
.unwrap() | ||
.try_deserialize() | ||
.map_err(|e| e.into()) | ||
} | ||
|
||
/// Create a new configuration from a file. | ||
pub fn from_file(path: &str) -> Result<Self> { | ||
base_config_builder() | ||
.add_source(File::with_name(path)) | ||
.build() | ||
.unwrap() | ||
.try_deserialize() | ||
.map_err(|e| e.into()) | ||
} | ||
} | ||
|
||
fn base_config_builder() -> ConfigBuilder<DefaultState> { | ||
Config::builder() | ||
// Start off by merging in the "default" configuration file | ||
.add_source(File::with_name("config/default")) | ||
// Add in settings from the environment (with a prefix of GATLING) | ||
// Eg.. `GATLING_FAIL_FAST=1 ./target/app` would set the `fail_fast` key | ||
.add_source(config::Environment::with_prefix("gatling")) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters