Skip to content

Commit

Permalink
fix: handle rustypes List, Tuple, HashMap, Struct
Browse files Browse the repository at this point in the history
  • Loading branch information
Prathiksha-Nataraja committed May 16, 2024
1 parent 51eefb4 commit f37a15f
Showing 1 changed file with 196 additions and 3 deletions.
199 changes: 196 additions & 3 deletions echo-library/src/common/starlark_modules.rs
Original file line number Diff line number Diff line change
Expand Up @@ -176,9 +176,202 @@ pub fn starlark_workflow_module(builder: &mut GlobalsBuilder) {
return Err(anyhow!("Value must be either true or false"));
}
}
RustType::HashMap(_, _) => {}
RustType::List(_) => {}
RustType::Tuple(_, _) => {}
RustType::HashMap(ref key_type, ref value_type) => {
let parsed_map = serde_json::from_str::<
serde_json::Map<String, serde_json::Value>,
>(&value_str)
.map_err(|_| {
anyhow!("Value must be a valid JSON object for HashMap type")
})?;

// Iterate through each key-value pair in the map and validate types
for (key, value) in parsed_map.iter() {
// Validate the key
match **key_type {
RustType::String => {
if !key.parse::<String>().is_ok() {
return Err(anyhow!(
"Key must be a string for HashMap(String, _)"
));
}
}
RustType::Int => {
if key.parse::<i64>().is_err() {
return Err(anyhow!(
"Key must be an integer for HashMap(Int, _)"
));
}
}
RustType::Uint => {
if key.parse::<u64>().is_err() {
return Err(anyhow!(
"Key must be an unsigned integer for HashMap(Uint, _)"
));
}
}
RustType::Float => {
if !value.is_f64() {
return Err(anyhow!(
"Key must be a float for HashMap(Float, _)"
));
}
}
_ => return Err(anyhow!("Unsupported key type for HashMap")),
}

// Validate the value
match **value_type {
RustType::String => {
if !value.is_string() {
return Err(anyhow!(
"Value must be a string for HashMap(_, String)"
));
}
}
RustType::Int => {
if !value.is_i64() {
return Err(anyhow!(
"Value must be an integer for HashMap(_, Int)"
));
}
}
RustType::Uint => {
if !value.is_u64() {
return Err(anyhow!("Value must be an unsigned integer for HashMap(_, Uint)"));
}
}
RustType::Float => {
if !value.is_f64() {
return Err(anyhow!(
"Value must be a float for HashMap(_, Float)"
));
}
}
_ => return Err(anyhow!("Unsupported value type for HashMap")),
}
}
}
RustType::List(ref item_type) => {
let parsed_array = serde_json::from_str::<Vec<serde_json::Value>>(
&value_str,
)
.map_err(|_| anyhow!("Value must be a valid JSON array for List type"))?;

// Check if each element in the array matches the expected item type
for element in parsed_array.iter() {
match **item_type {
RustType::String => {
if !element.is_string() {
return Err(anyhow!(
"List elements must be strings for List(String)"
));
}
}
RustType::Int => {
if !element.is_i64() && !element.is_i64() {
return Err(anyhow!(
"List elements must be integers for List(Int)"
));
}
}
RustType::Uint => {
if !element.is_f64() && !element.is_u64() {
return Err(anyhow!(
"List elements must be integers for List(Uint)"
));
}
}
RustType::Float => {
if !element.is_i64() && !element.is_f64() {
return Err(anyhow!(
"List elements must be integers for List(Float)"
));
}
}
_ => {}
}
}
}
RustType::Tuple(ref key_type, ref value_type) => {
// Parse the value_str as a JSON array
let parsed_tuple = serde_json::from_str::<Vec<serde_json::Value>>(
&value_str,
)
.map_err(|_| anyhow!("Value must be a valid JSON tuple for Tuple type"))?;

// Ensure the tuple has exactly two elements
if parsed_tuple.len() != 2 {
return Err(anyhow!("Tuple must have exactly two elements"));
}

// Validate the first element of the tuple
match **key_type {
RustType::String => {
if !parsed_tuple[0].is_string() {
return Err(anyhow!(
"First element of the tuple must be a string"
));
}
}
RustType::Int => {
if !parsed_tuple[0].is_i64() {
return Err(anyhow!(
"First element of the tuple must be an integer"
));
}
}
RustType::Uint => {
if !parsed_tuple[0].is_u64() {
return Err(anyhow!(
"First element of the tuple must be an unsigned integer"
));
}
}
RustType::Float => {
if !parsed_tuple[0].is_f64() {
return Err(anyhow!(
"First element of the tuple must be a float"
));
}
}

_ => {}
}

// Validate the second element of the tuple
match **value_type {
RustType::String => {
if !parsed_tuple[1].is_string() {
return Err(anyhow!(
"Second element of the tuple must be a string"
));
}
}
RustType::Int => {
if !parsed_tuple[1].is_i64() {
return Err(anyhow!(
"Second element of the tuple must be an integer"
));
}
}
RustType::Uint => {
if !parsed_tuple[1].is_u64() {
return Err(anyhow!(
"Second element of the tuple must be an unsigned integer"
));
}
}
RustType::Float => {
if !parsed_tuple[1].is_f64() {
return Err(anyhow!(
"Second element of the tuple must be a float"
));
}
}

_ => {}
}
}
RustType::Struct(_) => {}
_ => {
return Err(anyhow!("Unsupported input type for default value"));
Expand Down

0 comments on commit f37a15f

Please sign in to comment.