1 use proc_macro2;
2 use syn;
3 
4 use model::*;
5 use util::*;
6 
derive(item: syn::DeriveInput) -> Result<proc_macro2::TokenStream, Diagnostic>7 pub fn derive(item: syn::DeriveInput) -> Result<proc_macro2::TokenStream, Diagnostic> {
8     let model = Model::from_item(&item)?;
9 
10     let struct_name = &item.ident;
11     let field_ty = model
12         .fields()
13         .iter()
14         .map(|f| f.ty_for_deserialize())
15         .collect::<Result<Vec<_>, _>>()?;
16     let field_ty = &field_ty;
17     let build_expr = model.fields().iter().enumerate().map(|(i, f)| {
18         let i = syn::Index::from(i);
19         f.name.assign(parse_quote!(row.#i.into()))
20     });
21 
22     let (_, ty_generics, _) = item.generics.split_for_impl();
23     let mut generics = item.generics.clone();
24     generics
25         .params
26         .push(parse_quote!(__DB: diesel::backend::Backend));
27     generics.params.push(parse_quote!(__ST));
28     {
29         let where_clause = generics.where_clause.get_or_insert(parse_quote!(where));
30         where_clause
31             .predicates
32             .push(parse_quote!((#(#field_ty,)*): Queryable<__ST, __DB>));
33     }
34     let (impl_generics, _, where_clause) = generics.split_for_impl();
35 
36     Ok(wrap_in_dummy_mod(
37         model.dummy_mod_name("queryable"),
38         quote! {
39             use diesel::Queryable;
40 
41             impl #impl_generics Queryable<__ST, __DB> for #struct_name #ty_generics
42             #where_clause
43             {
44                 type Row = <(#(#field_ty,)*) as Queryable<__ST, __DB>>::Row;
45 
46                 fn build(row: Self::Row) -> Self {
47                     let row: (#(#field_ty,)*) = Queryable::build(row);
48                     Self {
49                         #(#build_expr,)*
50                     }
51                 }
52             }
53         },
54     ))
55 }
56