1
0
Fork 0
mirror of https://gitlab.com/msrd0/gotham-restful.git synced 2025-02-23 13:02:28 +00:00
deprecated-gotham-restful/derive/src/request_body.rs

90 lines
2.1 KiB
Rust
Raw Normal View History

use crate::util::CollectToResult;
2020-05-04 19:08:22 +02:00
use proc_macro2::{Ident, TokenStream};
2019-10-20 14:49:53 +00:00
use quote::quote;
use std::iter;
2019-10-20 14:49:53 +00:00
use syn::{
2020-05-03 23:25:48 +02:00
parenthesized,
2020-05-04 19:08:22 +02:00
parse::{Parse, ParseStream},
2019-10-20 14:49:53 +00:00
punctuated::Punctuated,
DeriveInput,
2019-10-20 14:49:53 +00:00
Generics,
Path,
2020-05-04 19:08:22 +02:00
Result,
2020-05-03 23:25:48 +02:00
Token
2019-10-20 14:49:53 +00:00
};
2020-05-03 23:25:48 +02:00
struct MimeList(Punctuated<Path, Token![,]>);
2019-10-20 14:49:53 +00:00
impl Parse for MimeList
{
2020-05-04 19:08:22 +02:00
fn parse(input: ParseStream) -> Result<Self>
2019-10-20 14:49:53 +00:00
{
let content;
let _paren = parenthesized!(content in input);
2020-05-03 23:25:48 +02:00
let list = Punctuated::parse_separated_nonempty(&content)?;
2019-10-20 14:49:53 +00:00
Ok(Self(list))
}
}
#[cfg(not(feature = "openapi"))]
2020-05-04 19:08:22 +02:00
fn impl_openapi_type(_ident : &Ident, _generics : &Generics) -> TokenStream
2019-10-20 14:49:53 +00:00
{
quote!()
}
#[cfg(feature = "openapi")]
2020-05-04 19:08:22 +02:00
fn impl_openapi_type(ident : &Ident, generics : &Generics) -> TokenStream
2019-10-20 14:49:53 +00:00
{
let krate = super::krate();
quote! {
impl #generics #krate::OpenapiType for #ident #generics
{
fn schema() -> #krate::OpenapiSchema
{
use #krate::{export::openapi::*, OpenapiSchema};
OpenapiSchema::new(SchemaKind::Type(Type::String(StringType {
format: VariantOrUnknownOrEmpty::Item(StringFormat::Binary),
..Default::default()
2019-10-20 14:49:53 +00:00
})))
}
}
}
}
2020-05-04 19:08:22 +02:00
pub fn expand_request_body(input : DeriveInput) -> Result<TokenStream>
2019-10-20 14:49:53 +00:00
{
let krate = super::krate();
let ident = input.ident;
let generics = input.generics;
let types = input.attrs.into_iter()
.filter(|attr| attr.path.segments.iter().last().map(|segment| segment.ident.to_string()) == Some("supported_types".to_string()))
.flat_map(|attr|
syn::parse2::<MimeList>(attr.tokens)
2020-05-04 19:08:22 +02:00
.map(|list| Box::new(list.0.into_iter().map(Ok)) as Box<dyn Iterator<Item = Result<Path>>>)
.unwrap_or_else(|err| Box::new(iter::once(Err(err)))))
.collect_to_result()?;
2019-10-20 14:49:53 +00:00
let types = match types {
ref types if types.is_empty() => quote!(None),
types => quote!(Some(vec![#(#types),*]))
};
let impl_openapi_type = impl_openapi_type(&ident, &generics);
2020-04-07 23:01:26 +02:00
Ok(quote! {
2019-10-20 14:49:53 +00:00
impl #generics #krate::RequestBody for #ident #generics
where #ident #generics : #krate::FromBody
{
fn supported_types() -> Option<Vec<#krate::Mime>>
{
#types
}
}
#impl_openapi_type
2020-04-07 23:01:26 +02:00
})
}