fix optional types for real

This commit is contained in:
2023-02-01 16:34:59 +01:00
parent f4581ba4cd
commit 26069a82a6
2 changed files with 431 additions and 379 deletions

View File

@@ -6,14 +6,33 @@ use crate::predicates::{
is_custom_scalar_type_ref, is_list_type, is_required_type_ref, is_scalar_type_ref,
};
//fn optional(t: rust::Tokens) -> impl FormatInto<Rust> {
// quote_fn! {"Option<$[const](t)>"}
//}
//
//fn required(t: rust::Tokens) -> impl FormatInto<Rust> {
// quote_fn! {"$[const](t)"}
//}
pub fn render_type_ref(inner: &TypeRef) -> eyre::Result<rust::Tokens> {
let extract_of_type = |t: &TypeRef| -> Option<TypeRef> {
return t.clone().of_type.map(|t| *t);
};
let (optional, inner) = if !is_required_type_ref(inner) {
(true, inner.clone())
} else {
(false, extract_of_type(inner).unwrap())
};
if is_list_type(&inner) {
if let Some(inner_of_type) = extract_of_type(inner) {
if let Some(inner_of_type) = extract_of_type(&inner) {
let inner_field = render_type_ref(&inner_of_type)?;
if optional {
return Ok(quote! {
Option<Vec<$inner_field>>
});
}
return Ok(quote! {
Vec<$inner_field>
});
@@ -21,8 +40,13 @@ pub fn render_type_ref(inner: &TypeRef) -> eyre::Result<rust::Tokens> {
}
if is_custom_scalar_type_ref(&inner) {
if let Some(inner_of_type) = extract_of_type(inner) {
if let Some(inner_of_type) = extract_of_type(&inner) {
let inner_field = render_type_ref(&inner_of_type)?;
if optional {
return Ok(quote! {
Option<$inner_field>
});
}
return Ok(quote! {
$inner_field
});
@@ -44,25 +68,34 @@ pub fn render_type_ref(inner: &TypeRef) -> eyre::Result<rust::Tokens> {
_ => eyre::bail!("missing type in the end of chain"),
};
if optional {
return Ok(quote! {
Option<$name>
});
}
return Ok(quote! {
$name
});
}
if !is_required_type_ref(inner) {
if let Some(inner_of_type) = extract_of_type(inner) {
let inner_field = render_type_ref(&inner_of_type)?;
if let Some(inner_type) = inner.of_type.as_ref() {
let inner_field = render_type_ref(&inner_type)?;
if optional {
return Ok(quote! {
Option<$inner_field>
});
}
}
if let Some(inner_type) = inner.of_type.as_ref() {
return render_type_ref(&inner_type);
return Ok(inner_field);
}
if let Some(name) = inner.name.as_ref() {
if optional {
return Ok(quote! {
Option<$name>
});
}
return Ok(quote! {
$name
});