Skip to content
This repository was archived by the owner on Jul 22, 2024. It is now read-only.

Commit 8ccab7c

Browse files
committed
Fix: generate Value from directly from &str
1 parent e4995b2 commit 8ccab7c

File tree

3 files changed

+97
-49
lines changed

3 files changed

+97
-49
lines changed

crates/starknet-contract-class/src/lib.rs

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@ use serde::Deserialize;
1515
use starknet_api::deprecated_contract_class::{ContractClassAbiEntry, EntryPoint};
1616
use std::{collections::HashMap, fs::File, io::BufReader, path::PathBuf};
1717

18+
// TODO: move this crate's functionality into SiR and remove the crate
19+
1820
pub type AbiType = Vec<ContractClassAbiEntry>;
1921

2022
#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
@@ -131,15 +133,15 @@ fn convert_entry_points(
131133
entry_points: HashMap<starknet_api::deprecated_contract_class::EntryPointType, Vec<EntryPoint>>,
132134
) -> HashMap<EntryPointType, Vec<ContractEntryPoint>> {
133135
let mut converted_entries: HashMap<EntryPointType, Vec<ContractEntryPoint>> = HashMap::new();
134-
for (entry_type, vec) in entry_points {
136+
for (entry_type, entry_points) in entry_points {
135137
let en_type = entry_type.into();
136138

137-
let contracts_entry_points = vec
139+
let contracts_entry_points = entry_points
138140
.into_iter()
139141
.map(|e| {
140142
let selector = Felt252::from_bytes_be(e.selector.0.bytes());
141143
let offset = e.offset.0;
142-
ContractEntryPoint { selector, offset }
144+
ContractEntryPoint::new(selector, offset)
143145
})
144146
.collect::<Vec<ContractEntryPoint>>();
145147

src/services/api/contract_classes/deprecated_contract_class.rs

Lines changed: 84 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,9 @@ use starknet_api::deprecated_contract_class::EntryPoint;
77
pub use starknet_contract_class::to_cairo_runner_program;
88
use starknet_contract_class::AbiType;
99
use starknet_contract_class::{ContractEntryPoint, EntryPointType};
10-
use std::{collections::HashMap, fs::File, io::BufReader, path::PathBuf};
10+
use std::collections::HashMap;
11+
use std::io::{BufReader, Read};
12+
use std::path::{Path, PathBuf};
1113

1214
// -------------------------------
1315
// Contract Class
@@ -33,12 +35,10 @@ impl ContractClass {
3335
abi: Option<AbiType>,
3436
) -> Result<Self, ContractClassError> {
3537
for entry_points in entry_points_by_type.values() {
36-
let mut index = 1;
37-
while let Some(entry_point) = entry_points.get(index) {
38-
if entry_point.selector() > entry_points[index - 1].selector() {
38+
for i in 1..entry_points.len() {
39+
if entry_points[i - 1].selector() > entry_points[i].selector() {
3940
return Err(ContractClassError::EntrypointError(entry_points.clone()));
4041
}
41-
index += 1;
4242
}
4343
}
4444

@@ -49,21 +49,29 @@ impl ContractClass {
4949
abi,
5050
})
5151
}
52+
53+
pub fn new_from_path<F>(path: F) -> Result<Self, ProgramError>
54+
where
55+
F: AsRef<Path>,
56+
{
57+
Self::try_from(std::fs::read_to_string(path)?.as_str())
58+
}
5259
}
5360

5461
// -------------------------------
5562
// From traits
5663
// -------------------------------
57-
impl TryFrom<starknet_api::deprecated_contract_class::ContractClass> for ContractClass {
64+
65+
impl TryFrom<&str> for ContractClass {
5866
type Error = ProgramError;
5967

60-
fn try_from(
61-
contract_class: starknet_api::deprecated_contract_class::ContractClass,
62-
) -> Result<Self, Self::Error> {
68+
fn try_from(s: &str) -> Result<Self, ProgramError> {
69+
let contract_class: starknet_api::deprecated_contract_class::ContractClass =
70+
serde_json::from_str(s)?;
6371
let program = to_cairo_runner_program(&contract_class.program)?;
6472
let entry_points_by_type =
6573
convert_entry_points(contract_class.clone().entry_points_by_type);
66-
let program_json = serde_json::to_value(&contract_class)?;
74+
let program_json = serde_json::from_str(s)?;
6775
Ok(ContractClass {
6876
program_json,
6977
program,
@@ -73,58 +81,52 @@ impl TryFrom<starknet_api::deprecated_contract_class::ContractClass> for Contrac
7381
}
7482
}
7583

76-
// -------------------
77-
// Helper Functions
78-
// -------------------
79-
80-
impl TryFrom<&str> for ContractClass {
84+
impl TryFrom<&Path> for ContractClass {
8185
type Error = ProgramError;
8286

83-
fn try_from(s: &str) -> Result<Self, ProgramError> {
84-
let raw_contract_class: starknet_api::deprecated_contract_class::ContractClass =
85-
serde_json::from_str(s)?;
86-
ContractClass::try_from(raw_contract_class)
87+
fn try_from(path: &Path) -> Result<Self, Self::Error> {
88+
Self::new_from_path(path)
8789
}
8890
}
8991

9092
impl TryFrom<PathBuf> for ContractClass {
9193
type Error = ProgramError;
9294

9395
fn try_from(path: PathBuf) -> Result<Self, Self::Error> {
94-
ContractClass::try_from(&path)
96+
Self::new_from_path(path)
9597
}
9698
}
9799

98100
impl TryFrom<&PathBuf> for ContractClass {
99101
type Error = ProgramError;
100102

101103
fn try_from(path: &PathBuf) -> Result<Self, Self::Error> {
102-
let file = File::open(path)?;
103-
let reader = BufReader::new(file);
104-
let raw_contract_class: starknet_api::deprecated_contract_class::ContractClass =
105-
serde_json::from_reader(reader)?;
106-
ContractClass::try_from(raw_contract_class)
104+
Self::new_from_path(path)
107105
}
108106
}
109107

110108
impl<T: std::io::Read> TryFrom<BufReader<T>> for ContractClass {
111109
type Error = ProgramError;
112110

113-
fn try_from(reader: BufReader<T>) -> Result<Self, Self::Error> {
114-
let raw_contract_class: starknet_api::deprecated_contract_class::ContractClass =
115-
serde_json::from_reader(reader)?;
116-
ContractClass::try_from(raw_contract_class)
111+
fn try_from(mut reader: BufReader<T>) -> Result<Self, Self::Error> {
112+
let mut s = String::new();
113+
reader.read_to_string(&mut s)?;
114+
Self::try_from(s.as_str())
117115
}
118116
}
119117

118+
// -------------------
119+
// Helper Functions
120+
// -------------------
121+
120122
fn convert_entry_points(
121123
entry_points: HashMap<starknet_api::deprecated_contract_class::EntryPointType, Vec<EntryPoint>>,
122124
) -> HashMap<EntryPointType, Vec<ContractEntryPoint>> {
123125
let mut converted_entries: HashMap<EntryPointType, Vec<ContractEntryPoint>> = HashMap::new();
124-
for (entry_type, vec) in entry_points {
126+
for (entry_type, entry_points) in entry_points {
125127
let en_type = entry_type.into();
126128

127-
let contracts_entry_points = vec
129+
let contracts_entry_points = entry_points
128130
.into_iter()
129131
.map(|e| {
130132
let selector = Felt252::from_bytes_be(e.selector.0.bytes());
@@ -149,15 +151,12 @@ mod tests {
149151
serde::deserialize_program::BuiltinName,
150152
};
151153
use starknet_contract_class::ParsedContractClass;
152-
use std::{fs, io::Read, str::FromStr};
154+
use std::{fs, str::FromStr};
153155

154156
#[test]
155157
fn deserialize_contract_class() {
156-
let mut serialized = String::new();
157-
158158
// This specific contract compiles with --no_debug_info
159-
File::open(PathBuf::from("starknet_programs/AccountPreset.json"))
160-
.and_then(|mut f| f.read_to_string(&mut serialized))
159+
let serialized = fs::read_to_string("starknet_programs/AccountPreset.json")
161160
.expect("should be able to read file");
162161

163162
let res = ContractClass::try_from(serialized.as_str());
@@ -205,13 +204,35 @@ mod tests {
205204
);
206205
}
207206

207+
#[test]
208+
fn test_contract_class_new_equals_raw_instantiation() {
209+
let contract_str = fs::read_to_string("starknet_programs/raw_contract_classes/0x4479c3b883b34f1eafa5065418225d78a11ee7957c371e1b285e4b77afc6dad.json").unwrap();
210+
211+
let parsed_contract_class = ParsedContractClass::try_from(contract_str.as_str()).unwrap();
212+
let contract_class = ContractClass {
213+
program_json: serde_json::Value::from_str(&contract_str).unwrap(),
214+
program: parsed_contract_class.program.clone(),
215+
entry_points_by_type: parsed_contract_class.entry_points_by_type.clone(),
216+
abi: parsed_contract_class.abi.clone(),
217+
};
218+
219+
let contract_class_new = ContractClass::new(
220+
serde_json::Value::from_str(&contract_str).unwrap(),
221+
parsed_contract_class.program,
222+
parsed_contract_class.entry_points_by_type,
223+
parsed_contract_class.abi,
224+
)
225+
.unwrap();
226+
227+
assert_eq!(contract_class, contract_class_new);
228+
}
229+
208230
#[test]
209231
fn test_compute_class_hash_0x4479c3b883b34f1eafa5065418225d78a11ee7957c371e1b285e4b77afc6dad_try_from(
210232
) {
211233
let contract_str = fs::read_to_string("starknet_programs/raw_contract_classes/0x4479c3b883b34f1eafa5065418225d78a11ee7957c371e1b285e4b77afc6dad.json").unwrap();
212234

213-
let contract_class =
214-
ContractClass::try_from(<String as AsRef<str>>::as_ref(&contract_str)).unwrap();
235+
let contract_class = ContractClass::try_from(contract_str.as_str()).unwrap();
215236

216237
assert_eq!(
217238
compute_deprecated_class_hash(&contract_class).unwrap(),
@@ -222,6 +243,31 @@ mod tests {
222243
);
223244
}
224245

246+
#[test]
247+
fn test_new_equals_try_from() {
248+
let contract_str = fs::read_to_string("starknet_programs/raw_contract_classes/0x4479c3b883b34f1eafa5065418225d78a11ee7957c371e1b285e4b77afc6dad.json").unwrap();
249+
250+
let parsed_contract_class = ParsedContractClass::try_from(contract_str.as_str()).unwrap();
251+
252+
let contract_class_new = ContractClass::new(
253+
serde_json::Value::from_str(&contract_str).unwrap(),
254+
parsed_contract_class.program,
255+
parsed_contract_class.entry_points_by_type,
256+
parsed_contract_class.abi,
257+
)
258+
.unwrap();
259+
260+
let contract_class = ContractClass::try_from(contract_str.as_str()).unwrap();
261+
262+
assert_eq!(contract_class.abi, contract_class_new.abi);
263+
assert_eq!(contract_class.program, contract_class_new.program);
264+
assert_eq!(contract_class.program_json, contract_class_new.program_json);
265+
assert_eq!(
266+
contract_class.entry_points_by_type,
267+
contract_class_new.entry_points_by_type
268+
);
269+
}
270+
225271
#[test]
226272
fn test_compute_class_hash_0x4479c3b883b34f1eafa5065418225d78a11ee7957c371e1b285e4b77afc6dad_new(
227273
) {

tests/complex_contracts/amm_contracts/amm_proxy.rs

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -427,8 +427,8 @@ fn amm_proxy_get_account_token_balance() {
427427
retdata: [200.into()].to_vec(),
428428
storage_read_values: [200.into()].to_vec(),
429429
execution_resources: ExecutionResources {
430-
n_steps: 94,
431-
n_memory_holes: 10,
430+
n_steps: 92,
431+
n_memory_holes: 11,
432432
builtin_instance_counter: HashMap::from([
433433
("pedersen_builtin".to_string(), 2),
434434
("range_check_builtin".to_string(), 3),
@@ -448,8 +448,8 @@ fn amm_proxy_get_account_token_balance() {
448448
calldata: calldata.clone(),
449449
retdata: [200.into()].to_vec(),
450450
execution_resources: ExecutionResources {
451-
n_steps: 153,
452-
n_memory_holes: 10,
451+
n_steps: 151,
452+
n_memory_holes: 11,
453453
builtin_instance_counter: HashMap::from([
454454
("pedersen_builtin".to_string(), 2),
455455
("range_check_builtin".to_string(), 3),
@@ -561,8 +561,8 @@ fn amm_proxy_swap() {
561561
storage_read_values: [100.into(), 1000.into(), 1000.into(), 100.into(), 200.into()]
562562
.to_vec(),
563563
execution_resources: ExecutionResources {
564-
n_steps: 824,
565-
n_memory_holes: 93,
564+
n_steps: 826,
565+
n_memory_holes: 92,
566566
builtin_instance_counter: HashMap::from([
567567
("pedersen_builtin".to_string(), 14),
568568
("range_check_builtin".to_string(), 41),
@@ -582,8 +582,8 @@ fn amm_proxy_swap() {
582582
calldata: calldata.clone(),
583583
retdata: expected_result,
584584
execution_resources: ExecutionResources {
585-
n_steps: 883,
586-
n_memory_holes: 93,
585+
n_steps: 885,
586+
n_memory_holes: 92,
587587
builtin_instance_counter: HashMap::from([
588588
("pedersen_builtin".to_string(), 14),
589589
("range_check_builtin".to_string(), 41),

0 commit comments

Comments
 (0)