Skip to content

Commit

Permalink
Rework code generation tests (#547)
Browse files Browse the repository at this point in the history
  • Loading branch information
andrzejressel authored Dec 4, 2024
1 parent 83861f2 commit df71d3f
Show file tree
Hide file tree
Showing 19 changed files with 662 additions and 1,018 deletions.
1 change: 1 addition & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 2 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -86,4 +86,5 @@ directories = "5.0"
reqwest = "0.12.5"
wit-component = "0.221.0"
wit-parser = "0.221.0"
bon = "3.0.0"
bon = "3.0.0"
proc-macro2 = "1.0.92"
7 changes: 4 additions & 3 deletions pulumi_wasm_generator_lib/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,10 @@ handlebars.workspace = true
regex.workspace = true
convert_case.workspace = true
serde_yaml.workspace = true
prettyplease = "0.2.25"
syn = "2.0.90"
proc-macro2 = "1.0.92"
prettyplease.workspace = true
syn.workspace = true
quote.workspace = true
proc-macro2.workspace = true

[dev-dependencies]
assert_cmd.workspace = true
21 changes: 21 additions & 0 deletions pulumi_wasm_generator_lib/src/code_generation/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
use crate::code_generation::rust_generation::generate_code;
use crate::code_generation::yaml::model::yaml_to_model;
use crate::code_generation::yaml::yaml_model::YamlFile;
use anyhow::anyhow;
use anyhow::Context;
use std::panic;
pub(crate) mod rust_generation;
mod tests;
pub(crate) mod yaml;

pub fn generate_code_from_string(
yaml: String,
package: &crate::model::Package,
) -> anyhow::Result<String> {
let yaml_file =
YamlFile::from_yaml(yaml.as_str()).context(format!("Failed to parse YAML: {}", yaml))?;
let example = panic::catch_unwind(|| yaml_to_model(yaml_file, package.name.clone(), package))
.map_err(|_| anyhow!("Failed to convert YAML to model"))
.context(format!("Failed to convert YAML {} to model", yaml))?;
generate_code(example)
}
Original file line number Diff line number Diff line change
@@ -1,23 +1,15 @@
use crate::code_generation::yaml::model::Example;
use crate::code_generation::yaml::model::Expression;
use crate::code_generation::yaml::model::Resource;
use crate::model::ElementId;
use crate::utils::escape_rust_name;
use crate::yaml::model::{yaml_to_model, Example, Expression, Resource};
use crate::yaml::yaml_model::YamlFile;
use anyhow::{anyhow, Context, Result};
use anyhow::Context;
use anyhow::Result;
use convert_case::Case;
use convert_case::Casing;
use quote::ToTokens;
use std::collections::BTreeMap;
use std::panic;
use syn::LitStr;
use syn::__private::ToTokens;

pub fn generate_code_from_string(yaml: String, package: &crate::model::Package) -> Result<String> {
let yaml_file =
YamlFile::from_yaml(yaml.as_str()).context(format!("Failed to parse YAML: {}", yaml))?;
let example = panic::catch_unwind(|| yaml_to_model(yaml_file, package.name.clone(), package))
.map_err(|_| anyhow!("Failed to convert YAML to model"))
.context(format!("Failed to convert YAML {} to model", yaml))?;
generate_code(example)
}

pub fn generate_code(example: Example) -> Result<String> {
let mut result = r"
Expand Down Expand Up @@ -139,47 +131,3 @@ fn generate_expression(expr: Expression) -> String {
}
}
}

#[cfg(test)]
mod tests {
use crate::code_generation::generate_code;
use crate::yaml::tests::{
access_rule, example_array, example_empty_properties, example_escape_string,
example_numbers,
};

#[test]
fn test_example_array() {
let model = example_array::get_model();
let code = generate_code(model).unwrap();
assert_eq!(example_array::get_rust_code(), code)
}

#[test]
fn test_access_rule() {
let model = access_rule::get_model();
let code = generate_code(model).unwrap();
assert_eq!(access_rule::get_rust_code(), code)
}

#[test]
fn test_without_parameters() {
let model = example_empty_properties::get_model();
let code = generate_code(model).unwrap();
assert_eq!(example_empty_properties::get_rust_code(), code)
}

#[test]
fn test_numbers() {
let model = example_numbers::get_model();
let code = generate_code(model).unwrap();
assert_eq!(example_numbers::get_rust_code(), code)
}

#[test]
fn test_string_escape() {
let model = example_escape_string::get_model();
let code = generate_code(model).unwrap();
assert_eq!(example_escape_string::get_rust_code(), code)
}
}
67 changes: 67 additions & 0 deletions pulumi_wasm_generator_lib/src/code_generation/tests.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
#[cfg(test)]
mod tests {
use crate::code_generation::yaml::model::yaml_to_model;
use crate::code_generation::yaml::tests::*;
use crate::code_generation::YamlFile;
use crate::{extract_schema_from_file, schema};

use crate::code_generation::rust_generation::generate_code;
use crate::code_generation::yaml::tests::{
example_array, example_empty_properties, example_escape_string, example_numbers,
};

macro_rules! yaml_deserialization_test {
($test_name:ident, $test_module:ident) => {
#[test]
fn $test_name() {
let yaml_file = YamlFile::from_yaml($test_module::YAML).unwrap();
let expected_yaml_file = $test_module::get_yaml_file();
assert_eq!(yaml_file, expected_yaml_file);
}
};
}

yaml_deserialization_test!(generate_yaml_complex_yaml, complex_yaml);

macro_rules! full_pipeline_test {
($test_name:ident, $package_name:expr, $test_module:ident) => {
#[test]
fn $test_name() {
let yaml_file = YamlFile::from_yaml($test_module::YAML).unwrap();
let expected_yaml_file = $test_module::get_yaml_file();
assert_eq!(yaml_file, expected_yaml_file);

let schema_package: schema::Package = extract_schema_from_file(
concat!("test_cases/", $package_name, ".json").as_ref(),
)
.unwrap();
let package = schema::to_model(&schema_package).unwrap();
let yaml_file = $test_module::get_yaml_file();
let result = yaml_to_model(yaml_file, $package_name.to_string(), &package);
assert_eq!(result, $test_module::get_model());

let model = $test_module::get_model();
let code = generate_code(model).unwrap();
assert_eq!($test_module::get_rust_code(), code);
}
};
}

full_pipeline_test!(full_pipeline_example_array, "cloudflare", example_array);
full_pipeline_test!(
full_pipeline_example_empty_properties,
"cloudflare",
example_empty_properties
);
full_pipeline_test!(
full_pipeline_example_escape_string,
"cloudflare",
example_escape_string
);
full_pipeline_test!(full_pipeline_example_numbers, "cloudflare", example_numbers);
full_pipeline_test!(
full_pipeline_example_variable,
"cloudflare",
example_variable
);
}
4 changes: 4 additions & 0 deletions pulumi_wasm_generator_lib/src/code_generation/yaml/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
pub(crate) mod model;
#[cfg(test)]
pub(crate) mod tests;
pub(crate) mod yaml_model;
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
use crate::code_generation::yaml::yaml_model::{YamlExpression, YamlFile, YamlResource};
use crate::model::{ElementId, GlobalType, Package, Ref, Type};
use crate::yaml::yaml_model::{YamlExpression, YamlFile, YamlResource};
use std::collections::{BTreeMap, HashMap};

struct PackageContext<'a> {
Expand Down Expand Up @@ -207,58 +207,3 @@ fn map_type(

Expression::Object(element_id.clone(), new_properties)
}

#[cfg(test)]
mod tests {
use super::*;
use crate::yaml::tests::{
access_rule, example_access_organization, example_array, example_numbers,
};
use crate::{extract_schema_from_file, schema};

#[test]
fn test_map_expression() {
let schema_package: schema::Package =
extract_schema_from_file("test_cases/cloudflare.json".as_ref()).unwrap();
let package = schema::to_model(&schema_package).unwrap();
let yaml_file = example_access_organization::get_yaml_file();

yaml_to_model(yaml_file, "cloudflare".to_string(), &package);
}

#[test]
fn test_access_rule() {
let schema_package: schema::Package =
extract_schema_from_file("test_cases/cloudflare.json".as_ref()).unwrap();
let package = schema::to_model(&schema_package).unwrap();
let yaml_file = access_rule::get_yaml_file();

let result = yaml_to_model(yaml_file, "cloudflare".to_string(), &package);

assert_eq!(result, access_rule::get_model());
}

#[test]
fn test_example_array() {
let schema_package: schema::Package =
extract_schema_from_file("test_cases/cloudflare.json".as_ref()).unwrap();
let package = schema::to_model(&schema_package).unwrap();
let yaml_file = example_array::get_yaml_file();

let result = yaml_to_model(yaml_file, "cloudflare".to_string(), &package);

assert_eq!(result, example_array::get_model());
}

#[test]
fn test_example_numbers() {
let schema_package: schema::Package =
extract_schema_from_file("test_cases/cloudflare.json".as_ref()).unwrap();
let package = schema::to_model(&schema_package).unwrap();
let yaml_file = example_numbers::get_yaml_file();

let result = yaml_to_model(yaml_file, "cloudflare".to_string(), &package);

assert_eq!(result, example_numbers::get_model());
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
use crate::code_generation::YamlFile;

//language=YAML
pub const YAML: &str = r#"
resources:
petstoreSchema:
type: cloudflare:ApiShieldSchema
name: petstore_schema
properties:
zoneId: 0da42c8d2132a9ddaf714f9e7c920711
name: myschema
kind: openapi_v3
validationEnabled: true
source:
fn::invoke:
Function: std:file
Arguments:
input: ./schemas/petstore.json
Return: result
"#;

pub fn get_yaml_file() -> YamlFile {
use crate::code_generation::yaml::yaml_model::{YamlExpression, YamlFile, YamlResource};
use std::collections::BTreeMap;

YamlFile {
resources: {
let mut resources = BTreeMap::new();
resources.insert(
"petstoreSchema".to_string(),
YamlResource {
type_: "cloudflare:ApiShieldSchema".to_string(),
name: Some("petstore_schema".to_string()),
properties: {
let mut properties = BTreeMap::new();
properties.insert(
"zoneId".to_string(),
YamlExpression::String("0da42c8d2132a9ddaf714f9e7c920711".to_string()),
);
properties.insert(
"name".to_string(),
YamlExpression::String("myschema".to_string()),
);
properties.insert(
"kind".to_string(),
YamlExpression::String("openapi_v3".to_string()),
);
properties.insert(
"validationEnabled".to_string(),
YamlExpression::Boolean(true),
);
properties.insert(
"source".to_string(),
YamlExpression::Object({
let mut source = BTreeMap::new();
source.insert(
"fn::invoke".to_string(),
YamlExpression::Object({
let mut fn_invoke = BTreeMap::new();
fn_invoke.insert(
"Function".to_string(),
YamlExpression::String("std:file".to_string()),
);
fn_invoke.insert(
"Arguments".to_string(),
YamlExpression::Object({
let mut arguments = BTreeMap::new();
arguments.insert(
"input".to_string(),
YamlExpression::String(
"./schemas/petstore.json".to_string(),
),
);
arguments
}),
);
fn_invoke.insert(
"Return".to_string(),
YamlExpression::String("result".to_string()),
);
fn_invoke
}),
);
source
}),
);
properties
},
},
);
resources
},
}
}
Loading

0 comments on commit df71d3f

Please sign in to comment.