diff --git a/Cargo.lock b/Cargo.lock index f52d966..8ac7bcc 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1124,6 +1124,7 @@ dependencies = [ "quote", "serde", "serde_json", + "serde_yaml", "syn 2.0.23", "tera", "tracing-ez", @@ -1669,9 +1670,9 @@ dependencies = [ [[package]] name = "serde_yaml" -version = "0.9.22" +version = "0.9.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "452e67b9c20c37fa79df53201dc03839651086ed9bbe92b3ca585ca9fdaa7d85" +checksum = "1a49e178e4452f45cb61d0cd8cebc1b0fafd3e41929e996cef79aa3aca91f574" dependencies = [ "indexmap 2.0.0", "itoa", diff --git a/Cargo.toml b/Cargo.toml index adb0db6..d9468e6 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,4 +1,5 @@ [workspace] +resolver = "2" members = [ "libninja", "macro", diff --git a/Justfile b/Justfile index c314e3d..ff1683c 100644 --- a/Justfile +++ b/Justfile @@ -96,6 +96,7 @@ generate: cargo run -- gen --name $SERVICE --output-dir $REPO_DIR --generator $SOURCEGEN --github $REPO --version $VERSION $LIBRARY $SPEC test *ARGS: + cd core && cargo test -- "$@" cd libninja && cargo test -- "$@" alias t := test diff --git a/core/Cargo.toml b/core/Cargo.toml index d5b16a9..a74c8c2 100644 --- a/core/Cargo.toml +++ b/core/Cargo.toml @@ -20,3 +20,6 @@ syn = "2.0" ln-mir = { path = "../mir" } include_dir = "0.7.3" tera = "1.19.0" + +[dev-dependencies] +serde_yaml = "0.9.25" \ No newline at end of file diff --git a/core/src/extractor/pet_tag.yaml b/core/src/extractor/pet_tag.yaml new file mode 100644 index 0000000..7f19041 --- /dev/null +++ b/core/src/extractor/pet_tag.yaml @@ -0,0 +1,13 @@ +allOf: + - type: object + required: + - eye-color + properties: + eye-color: + type: string + enum: + - blue + - brown + - green + weight: + type: integer \ No newline at end of file diff --git a/core/src/extractor/record.rs b/core/src/extractor/record.rs index 7bfb36d..f19b690 100644 --- a/core/src/extractor/record.rs +++ b/core/src/extractor/record.rs @@ -119,7 +119,10 @@ fn create_record_from_all_of(name: &str, all_of: &[ReferenceOr], schema_ match item.properties() { Some(props) => { for (name, schema) in props { - let field = create_field(schema, spec); + let mut field = create_field(schema, spec); + if !item.required(name) { + field.optional = true; + } fields.insert(Name::new(name), field); } } @@ -154,3 +157,22 @@ pub fn extract_records(spec: &OpenAPI) -> Result> { .collect::>()?; Ok(result) } + +#[cfg(test)] +mod tests { + use openapiv3::{OpenAPI, ReferenceOr, Schema, SchemaData, SchemaKind}; + use crate::extractor::record::create_record_from_all_of; + + #[test] + fn test_all_of_required_set_correctly() { + let mut additional_props: Schema = serde_yaml::from_str(include_str!("./pet_tag.yaml")).unwrap(); + let SchemaKind::AllOf { all_of } = &additional_props.schema_kind else { panic!() }; + let spec = OpenAPI::default(); + let rec = create_record_from_all_of("PetTag", &all_of, &SchemaData::default(), &spec); + let mut fields = rec.fields(); + let eye_color = fields.next().unwrap(); + let weight = fields.next().unwrap(); + assert_eq!(eye_color.optional, false); + assert_eq!(weight.optional, true); + } +} \ No newline at end of file diff --git a/core/src/hir.rs b/core/src/hir.rs index 99c322e..6ac2527 100644 --- a/core/src/hir.rs +++ b/core/src/hir.rs @@ -233,6 +233,7 @@ pub struct StrEnum { pub variants: Vec, } +// an object type in the HIR #[derive(Debug, Clone)] pub enum Record { Struct(Struct), diff --git a/libninja/tests/all_of/main.rs b/libninja/tests/all_of/main.rs index 6f31b1c..29a9678 100644 --- a/libninja/tests/all_of/main.rs +++ b/libninja/tests/all_of/main.rs @@ -35,6 +35,7 @@ fn test_transaction() { let record = record_for_schema("Transaction", TRANSACTION, &spec); let code = formatted_code(record); + println!("{}", code); assert_eq!(code, TRANSACTION_RS); } diff --git a/libninja/tests/all_of/transaction.rs b/libninja/tests/all_of/transaction.rs index 293c03f..24f35c1 100644 --- a/libninja/tests/all_of/transaction.rs +++ b/libninja/tests/all_of/transaction.rs @@ -6,12 +6,15 @@ pub struct Transaction { pub authorized_date: Option, #[serde(skip_serializing_if = "Option::is_none")] pub authorized_datetime: Option>, - pub counterparties: Vec, + #[serde(skip_serializing_if = "Option::is_none")] + pub counterparties: Option>, #[serde(skip_serializing_if = "Option::is_none")] pub datetime: Option>, pub payment_channel: String, - pub personal_finance_category: String, - pub personal_finance_category_icon_url: String, + #[serde(skip_serializing_if = "Option::is_none")] + pub personal_finance_category: Option, + #[serde(skip_serializing_if = "Option::is_none")] + pub personal_finance_category_icon_url: Option, pub transaction_code: String, } impl std::fmt::Display for Transaction {