Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add sozo stats back #2684

Merged
merged 3 commits into from
Nov 13, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion bin/sozo/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ scarb.workspace = true
scarb-ui.workspace = true
semver.workspace = true
serde.workspace = true
serde_json.workspace = true
smol_str.workspace = true
sozo-ops.workspace = true
sozo-walnut = { workspace = true, optional = true }
Expand All @@ -43,7 +44,6 @@ starknet.workspace = true
starknet-crypto.workspace = true
thiserror.workspace = true
toml.workspace = true
tokio.workspace = true
tracing.workspace = true
tracing-log.workspace = true
tracing-subscriber.workspace = true
Expand All @@ -55,6 +55,7 @@ reqwest = { workspace = true, features = [ "json" ], optional = true }
dojo-test-utils = { workspace = true, features = [ "build-examples" ] }
katana-runner.workspace = true
serde_json.workspace = true
tokio.workspace = true

[features]
default = [ "controller", "walnut" ]
Expand Down
210 changes: 198 additions & 12 deletions bin/sozo/src/commands/build.rs
Original file line number Diff line number Diff line change
@@ -1,10 +1,17 @@
use std::cmp::Reverse;

use anyhow::Result;
use clap::{Args, Parser};
use colored::{ColoredString, Colorize};
use dojo_bindgen::{BuiltinPlugins, PluginManager};
use dojo_world::local::{ResourceLocal, WorldLocal};
use dojo_world::ResourceType;
use scarb::core::{Config, Package, TargetKind};
use scarb::ops::CompileOpts;
use scarb_ui::args::{FeaturesSpec, PackagesFilter};
use sozo_scarbext::WorkspaceExt;
use tabled::settings::Style;
use tabled::{Table, Tabled};
use tracing::debug;

use crate::commands::check_package_dojo_version;
Expand All @@ -27,9 +34,6 @@
#[arg(help = "Output directory.", default_value = "bindings")]
pub bindings_output: String,

#[arg(long, help = "Display statistics about the compiled contracts")]
pub stats: bool,

/// Specify the features to activate.
#[command(flatten)]
pub features: FeaturesSpec,
Expand All @@ -38,9 +42,37 @@
#[command(flatten)]
pub packages: Option<PackagesFilter>,

#[arg(long)]
#[arg(help = "Output the Sierra debug information for the compiled contracts.")]
pub output_debug_info: bool,
/// Display statistics about the compiled contracts.
#[command(flatten)]
pub stats: StatOptions,
}

#[derive(Debug, Clone, Args, Default, PartialEq)]
#[command(next_help_heading = "Statistics options")]
pub struct StatOptions {
#[arg(long = "stats.by-tag")]
#[arg(help = "Sort the stats by tag.")]
#[arg(conflicts_with_all = ["stats.by-sierra-mb", "stats.by-sierra-felts", "stats.by-casm-felts"])]
#[arg(default_value_t = false)]
pub sort_by_tag: bool,

Check warning on line 57 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L56-L57

Added lines #L56 - L57 were not covered by tests

#[arg(long = "stats.by-sierra-mb")]
#[arg(help = "Sort the stats by Sierra file size in MB.")]
#[arg(conflicts_with_all = ["stats.by-tag", "stats.by-sierra-felts", "stats.by-casm-felts"])]
#[arg(default_value_t = false)]
pub sort_by_sierra_mb: bool,

Check warning on line 63 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L62-L63

Added lines #L62 - L63 were not covered by tests

#[arg(long = "stats.by-sierra-felts")]
#[arg(help = "Sort the stats by Sierra program size in felts.")]
#[arg(conflicts_with_all = ["stats.by-tag", "stats.by-sierra-mb", "stats.by-casm-felts"])]
#[arg(default_value_t = false)]
pub sort_by_sierra_felts: bool,

Check warning on line 69 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L68-L69

Added lines #L68 - L69 were not covered by tests

#[arg(long = "stats.by-casm-felts")]
#[arg(help = "Sort the stats by Casm bytecode size in felts.")]
#[arg(conflicts_with_all = ["stats.by-tag", "stats.by-sierra-mb", "stats.by-sierra-felts"])]
#[arg(default_value_t = false)]
pub sort_by_casm_felts: bool,

Check warning on line 75 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L74-L75

Added lines #L74 - L75 were not covered by tests
}

impl BuildArgs {
Expand Down Expand Up @@ -104,10 +136,59 @@

// TODO: check about the skip migration as now we process the metadata
// directly during the compilation to get the data we need from it.
tokio::runtime::Runtime::new()
.unwrap()
.block_on(bindgen.generate(None))
.expect("Error generating bindings");
config.tokio_handle().block_on(bindgen.generate(None)).expect("Error generating bindings");

if self.stats != StatOptions::default() {
let world = WorldLocal::from_directory(
ws.target_dir_profile().to_string(),
ws.load_profile_config().unwrap(),
)?;

Check warning on line 145 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L139-L145

Added lines #L139 - L145 were not covered by tests

let world_stat = world.to_stat_item();
let mut stats = vec![world_stat];

Check warning on line 148 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L147-L148

Added lines #L147 - L148 were not covered by tests

for r in world.resources.values() {
if r.resource_type() != ResourceType::Namespace {
stats.push(r.to_stat_item());
}

Check warning on line 153 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L150-L153

Added lines #L150 - L153 were not covered by tests
}

if self.stats.sort_by_tag {
stats.sort_by_key(|s| s.tag.clone());
} else if self.stats.sort_by_sierra_mb {
stats.sort_by_key(|s| Reverse(s.sierra_file_size));
} else if self.stats.sort_by_sierra_felts {
stats.sort_by_key(|s| Reverse(s.sierra_program_size));
} else if self.stats.sort_by_casm_felts {
stats.sort_by_key(|s| Reverse(s.casm_bytecode_size));
}

Check warning on line 164 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L156-L164

Added lines #L156 - L164 were not covered by tests

let mut table = Table::new(stats.iter().map(StatItemPrint::from).collect::<Vec<_>>());
table.with(Style::psql());

println!();
println!("{table}");

if stats.iter().all(|s| s.casm_bytecode_size == 0) {
println!(
"{}",
r#"
All the casm bytecode sizes are 0, did you forget to enable casm compilation?
To enable casm compilation, add the following to your Scarb.toml:

[[target.starknet-contract]]
sierra = true
casm = true
"#
.bright_yellow()
);
}

Check warning on line 185 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L166-L185

Added lines #L166 - L185 were not covered by tests

println!(
"\nRefer to https://docs.starknet.io/tools/limits-and-triggers/ for more \
information about the public networks limits."
);
}

Check warning on line 191 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L187-L191

Added lines #L187 - L191 were not covered by tests

Ok(())
}
Expand All @@ -124,9 +205,114 @@
typescript_v2: false,
unity: false,
bindings_output: "bindings".to_string(),
stats: false,
stats: StatOptions::default(),

Check warning on line 208 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L208

Added line #L208 was not covered by tests
packages: None,
output_debug_info: false,
}
}
}

trait ContractStats {
fn to_stat_item(&self) -> StatItem;
fn sierra_file_size(&self) -> Result<usize>;
fn sierra_program_felt_size(&self) -> usize;
fn casm_program_felt_size(&self) -> usize;
}

#[derive(Debug, Tabled)]

Check warning on line 221 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L221

Added line #L221 was not covered by tests
struct StatItemPrint {
#[tabled(rename = "")]
tag: ColoredString,
#[tabled(rename = "Sierra size (byte)")]
sierra_file_size: ColoredString,
#[tabled(rename = "Sierra felts")]
sierra_program_size: ColoredString,
#[tabled(rename = "Casm felts")]
casm_bytecode_size: ColoredString,
}

impl From<&StatItem> for StatItemPrint {
fn from(item: &StatItem) -> Self {

Check warning on line 234 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L234

Added line #L234 was not covered by tests
const MAX_SIERRA_SIZE_BYTES: usize = 4_089_446;
const MAX_CASM_FELTS: usize = 81_290;

let tag = if item.tag == "world" {
"World".to_string().bright_magenta()

Check warning on line 239 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L238-L239

Added lines #L238 - L239 were not covered by tests
} else {
item.tag.to_string().bright_blue()

Check warning on line 241 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L241

Added line #L241 was not covered by tests
};

let sierra_file_size = if item.sierra_file_size > MAX_SIERRA_SIZE_BYTES {
item.sierra_file_size.to_string().bright_red()

Check warning on line 245 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L244-L245

Added lines #L244 - L245 were not covered by tests
} else {
item.sierra_file_size.to_string().bright_green()

Check warning on line 247 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L247

Added line #L247 was not covered by tests
};

let sierra_program_size = item.sierra_program_size.to_string().bright_black();

Check warning on line 250 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L250

Added line #L250 was not covered by tests

let casm_bytecode_size = if item.casm_bytecode_size > MAX_CASM_FELTS {
item.casm_bytecode_size.to_string().bright_red()

Check warning on line 253 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L252-L253

Added lines #L252 - L253 were not covered by tests
} else {
item.casm_bytecode_size.to_string().bright_green()

Check warning on line 255 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L255

Added line #L255 was not covered by tests
};

Self { tag, sierra_file_size, sierra_program_size, casm_bytecode_size }
}

Check warning on line 259 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L258-L259

Added lines #L258 - L259 were not covered by tests
}

#[derive(Debug)]
struct StatItem {
tag: String,
sierra_file_size: usize,
sierra_program_size: usize,
casm_bytecode_size: usize,
}

impl ContractStats for ResourceLocal {
fn to_stat_item(&self) -> StatItem {
StatItem {
tag: self.tag(),
sierra_file_size: self.sierra_file_size().unwrap(),
sierra_program_size: self.sierra_program_felt_size(),
casm_bytecode_size: self.casm_program_felt_size(),
}
}

Check warning on line 278 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L271-L278

Added lines #L271 - L278 were not covered by tests

fn sierra_file_size(&self) -> Result<usize> {
// Easiest way to get the file size if by reserializing into the original json
// the class file.
Ok(serde_json::to_string(&self.common().class)?.len())
}

Check warning on line 284 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L280-L284

Added lines #L280 - L284 were not covered by tests

fn sierra_program_felt_size(&self) -> usize {
self.common().class.sierra_program.len()
}

Check warning on line 288 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L286-L288

Added lines #L286 - L288 were not covered by tests

fn casm_program_felt_size(&self) -> usize {
self.common().casm_class.as_ref().map_or(0, |casm| casm.bytecode.len())
}

Check warning on line 292 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L290-L292

Added lines #L290 - L292 were not covered by tests
}

impl ContractStats for WorldLocal {
fn to_stat_item(&self) -> StatItem {
StatItem {
tag: "world".to_string(),
sierra_file_size: self.sierra_file_size().unwrap(),
sierra_program_size: self.sierra_program_felt_size(),
casm_bytecode_size: self.casm_program_felt_size(),
}
}

Check warning on line 303 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L296-L303

Added lines #L296 - L303 were not covered by tests

fn sierra_file_size(&self) -> Result<usize> {
// Easiest way to get the file size if by reserializing into the original json
// the class file.
Ok(serde_json::to_string(&self.class)?.len())
}

Check warning on line 309 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L305-L309

Added lines #L305 - L309 were not covered by tests

fn sierra_program_felt_size(&self) -> usize {
self.class.sierra_program.len()
}

Check warning on line 313 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L311-L313

Added lines #L311 - L313 were not covered by tests

fn casm_program_felt_size(&self) -> usize {
self.casm_class.as_ref().map_or(0, |casm| casm.bytecode.len())
}

Check warning on line 317 in bin/sozo/src/commands/build.rs

View check run for this annotation

Codecov / codecov/patch

bin/sozo/src/commands/build.rs#L315-L317

Added lines #L315 - L317 were not covered by tests
}
1 change: 1 addition & 0 deletions crates/dojo/world/src/contracts/contract_info.rs
Original file line number Diff line number Diff line change
Expand Up @@ -190,6 +190,7 @@ mod tests {
},
abi: vec![],
},
casm_class: None,
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codebase verification

ohayo! sensei!

Inconsistency Found in CommonLocalInfo Struct Definitions

The casm_class field is missing in some CommonLocalInfo struct definitions. Please ensure all instances include the casm_class field for consistency.

  • crates/dojo/world/src/local/resource.rs
  • crates/dojo/world/src/contracts/contract_info.rs
🔗 Analysis chain

Ohayo! The CASM class field addition looks good, sensei!

The addition of casm_class: None in the test's CommonLocalInfo structure aligns well with the PR's objective of enhancing CASM class handling.

Let's verify the consistency of this field across related files:

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Check for consistent CommonLocalInfo structure usage
# Expected: All CommonLocalInfo structs should have casm_class field

# Search for CommonLocalInfo struct definitions
ast-grep --pattern 'struct CommonLocalInfo {
  $$$
}'

# Search for CommonLocalInfo instantiations
rg -A 5 'CommonLocalInfo \{'

Length of output: 6953

class_hash: felt!("0x2222"),
casm_class_hash: felt!("0x2222"),
},
Expand Down
3 changes: 3 additions & 0 deletions crates/dojo/world/src/diff/compare.rs
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,7 @@ mod tests {
name: "model1".to_string(),
namespace: "ns1".to_string(),
class: empty_sierra_class(),
casm_class: None,
class_hash: Felt::ZERO,
casm_class_hash: Felt::ZERO,
},
Expand Down Expand Up @@ -127,6 +128,7 @@ mod tests {
name: "event1".to_string(),
namespace: "ns1".to_string(),
class: empty_sierra_class(),
casm_class: None,
class_hash: Felt::ZERO,
casm_class_hash: Felt::ZERO,
},
Expand Down Expand Up @@ -175,6 +177,7 @@ mod tests {
name: "contract1".to_string(),
namespace: "ns1".to_string(),
class: empty_sierra_class(),
casm_class: None,
class_hash: Felt::ZERO,
casm_class_hash: Felt::ZERO,
},
Expand Down
2 changes: 2 additions & 0 deletions crates/dojo/world/src/diff/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -379,6 +379,7 @@ mod tests {
name: "c".to_string(),
namespace: ns.clone(),
class: empty_sierra_class(),
casm_class: None,
class_hash: Felt::ONE,
casm_class_hash: Felt::ZERO,
},
Expand Down Expand Up @@ -417,6 +418,7 @@ mod tests {
name: "c".to_string(),
namespace: ns.clone(),
class: empty_sierra_class(),
casm_class: None,
class_hash: Felt::TWO,
casm_class_hash: Felt::ZERO,
},
Expand Down
Loading
Loading