basic handling of String newtypes and enumerations
This commit is contained in:
parent
dd73bac4c0
commit
deace5928c
82
src/main.rs
82
src/main.rs
|
@ -6,7 +6,7 @@ use serde::Deserialize;
|
||||||
use std::collections::{BTreeMap, BTreeSet, HashMap, HashSet};
|
use std::collections::{BTreeMap, BTreeSet, HashMap, HashSet};
|
||||||
use std::fs::{File, OpenOptions};
|
use std::fs::{File, OpenOptions};
|
||||||
use std::io::Write;
|
use std::io::Write;
|
||||||
use std::path::{PathBuf, Path};
|
use std::path::{Path, PathBuf};
|
||||||
|
|
||||||
mod template;
|
mod template;
|
||||||
|
|
||||||
|
@ -438,6 +438,8 @@ enum TypeDetails {
|
||||||
* order in the generated code.
|
* order in the generated code.
|
||||||
*/
|
*/
|
||||||
Object(BTreeMap<String, TypeId>),
|
Object(BTreeMap<String, TypeId>),
|
||||||
|
NewType(TypeId),
|
||||||
|
Enumeration(Vec<String>),
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
@ -541,6 +543,26 @@ impl TypeSpace {
|
||||||
format!("[OBJECT {} !NONAME?]", tid.0)
|
format!("[OBJECT {} !NONAME?]", tid.0)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
TypeDetails::NewType(itid) => {
|
||||||
|
if let Some(ite) = self.id_to_entry.get(&itid) {
|
||||||
|
if let Some(n) = &ite.name {
|
||||||
|
return format!("newtype of {} <{}>", n, itid.0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* If there is no name attached, we should try a
|
||||||
|
* recursive describe.
|
||||||
|
*/
|
||||||
|
format!("newtype of {}", self.describe(itid))
|
||||||
|
}
|
||||||
|
TypeDetails::Enumeration(_) => {
|
||||||
|
if let Some(n) = &te.name {
|
||||||
|
format!("enum {}", n)
|
||||||
|
} else {
|
||||||
|
format!("[ENUMERATION {} !NONAME?]", tid.0)
|
||||||
|
}
|
||||||
|
}
|
||||||
TypeDetails::Unknown => {
|
TypeDetails::Unknown => {
|
||||||
format!("[UNKNOWN {}]", tid.0)
|
format!("[UNKNOWN {}]", tid.0)
|
||||||
}
|
}
|
||||||
|
@ -566,7 +588,9 @@ impl TypeSpace {
|
||||||
TypeDetails::Optional(itid) => {
|
TypeDetails::Optional(itid) => {
|
||||||
Ok(format!("Option<{}>", self.render_type(itid, in_mod)?))
|
Ok(format!("Option<{}>", self.render_type(itid, in_mod)?))
|
||||||
}
|
}
|
||||||
TypeDetails::Object(_) => {
|
TypeDetails::Object(_)
|
||||||
|
| TypeDetails::NewType(_)
|
||||||
|
| TypeDetails::Enumeration(_) => {
|
||||||
if let Some(n) = &te.name {
|
if let Some(n) = &te.name {
|
||||||
if in_mod {
|
if in_mod {
|
||||||
Ok(n.to_string())
|
Ok(n.to_string())
|
||||||
|
@ -720,8 +744,28 @@ impl TypeSpace {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
Empty => {
|
Empty => {
|
||||||
|
use TypeDetails::{Enumeration, NewType};
|
||||||
|
|
||||||
|
if !st.enumeration.is_empty() {
|
||||||
|
if let Some(name) = name {
|
||||||
|
(
|
||||||
|
Some(name.to_string()),
|
||||||
|
Enumeration(st.enumeration.clone()),
|
||||||
|
)
|
||||||
|
} else {
|
||||||
|
bail!("enumeration without name: {:?}", st);
|
||||||
|
}
|
||||||
|
} else if let Some(name) = name {
|
||||||
|
/*
|
||||||
|
* Create a newtype struct for strings that have
|
||||||
|
* a name of their own.
|
||||||
|
*/
|
||||||
|
let id = self.id_for_name("String");
|
||||||
|
(Some(name.to_string()), NewType(id))
|
||||||
|
} else {
|
||||||
(Some("String".to_string()), TypeDetails::Basic)
|
(Some("String".to_string()), TypeDetails::Basic)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
x => {
|
x => {
|
||||||
bail!("XXX string format {:?}", x);
|
bail!("XXX string format {:?}", x);
|
||||||
}
|
}
|
||||||
|
@ -906,6 +950,37 @@ fn gen(api: &OpenAPI, ts: &mut TypeSpace) -> Result<String> {
|
||||||
a(" }");
|
a(" }");
|
||||||
a("");
|
a("");
|
||||||
}
|
}
|
||||||
|
TypeDetails::NewType(tid) => {
|
||||||
|
a(" #[derive(Serialize, Deserialize, Debug)]");
|
||||||
|
a(&format!(
|
||||||
|
" pub struct {}({});",
|
||||||
|
te.name.as_deref().unwrap(),
|
||||||
|
ts.render_type(tid, true)?,
|
||||||
|
));
|
||||||
|
a("");
|
||||||
|
}
|
||||||
|
TypeDetails::Enumeration(list) => {
|
||||||
|
a(" #[derive(Serialize, Deserialize, Debug)]");
|
||||||
|
a(&format!(" pub enum {} {{", te.name.as_deref().unwrap()));
|
||||||
|
for name in list.iter() {
|
||||||
|
/*
|
||||||
|
* Attempt to make the first letter a capital letter.
|
||||||
|
*/
|
||||||
|
let mut name = name.chars().collect::<Vec<_>>();
|
||||||
|
if name[0].is_ascii_alphabetic() {
|
||||||
|
name[0] = name[0].to_ascii_uppercase();
|
||||||
|
}
|
||||||
|
|
||||||
|
a(
|
||||||
|
&format!(
|
||||||
|
" {},",
|
||||||
|
name.iter().collect::<String>(),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
a(" }");
|
||||||
|
a("");
|
||||||
|
}
|
||||||
TypeDetails::Basic => {}
|
TypeDetails::Basic => {}
|
||||||
TypeDetails::Unknown => {}
|
TypeDetails::Unknown => {}
|
||||||
TypeDetails::Array(_) => {}
|
TypeDetails::Array(_) => {}
|
||||||
|
@ -1292,8 +1367,7 @@ fn main() -> Result<()> {
|
||||||
percent-encoding = \"2.1\"\n\
|
percent-encoding = \"2.1\"\n\
|
||||||
reqwest = {{ version = \"0.11\", features = [\"json\"] }}\n\
|
reqwest = {{ version = \"0.11\", features = [\"json\"] }}\n\
|
||||||
serde = {{ version = \"1\", features = [\"derive\"] }}\n",
|
serde = {{ version = \"1\", features = [\"derive\"] }}\n",
|
||||||
name,
|
name, version,
|
||||||
version,
|
|
||||||
);
|
);
|
||||||
save(&toml, tomlout.as_str())?;
|
save(&toml, tomlout.as_str())?;
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue