1
1
use proc_macro:: TokenStream ;
2
2
3
- use devise:: { DeriveGenerator , FromMeta , MapperBuild , Support , ValidatorBuild } ;
4
3
use devise:: proc_macro2_diagnostics:: SpanDiagnosticExt ;
5
4
use devise:: syn:: { self , spanned:: Spanned } ;
5
+ use devise:: { DeriveGenerator , FromMeta , MapperBuild , Support , ValidatorBuild } ;
6
6
7
7
const ONE_DATABASE_ATTR : & str = "missing `#[database(\" name\" )]` attribute" ;
8
8
const ONE_UNNAMED_FIELD : & str = "struct must have exactly one unnamed field" ;
@@ -16,95 +16,89 @@ struct DatabaseAttribute {
16
16
pub fn derive_database ( input : TokenStream ) -> TokenStream {
17
17
DeriveGenerator :: build_for ( input, quote ! ( impl rocket_db_pools:: Database ) )
18
18
. support ( Support :: TupleStruct )
19
- . validator ( ValidatorBuild :: new ( )
20
- . struct_validate ( |_, s| {
21
- if s. fields . len ( ) == 1 {
22
- Ok ( ( ) )
23
- } else {
24
- Err ( s. span ( ) . error ( ONE_UNNAMED_FIELD ) )
25
- }
26
- } )
27
- )
28
- . outer_mapper ( MapperBuild :: new ( )
29
- . struct_map ( |_, s| {
30
- let pool_type = match & s. fields {
31
- syn:: Fields :: Unnamed ( f) => & f. unnamed [ 0 ] . ty ,
32
- _ => unreachable ! ( "Support::TupleStruct" ) ,
33
- } ;
34
-
35
- let decorated_type = & s. ident ;
36
- let db_ty = quote_spanned ! ( decorated_type. span( ) =>
37
- <#decorated_type as rocket_db_pools:: Database >
38
- ) ;
39
-
40
- quote_spanned ! { decorated_type. span( ) =>
41
- impl From <#pool_type> for #decorated_type {
42
- fn from( pool: #pool_type) -> Self {
43
- Self ( pool)
44
- }
19
+ . validator ( ValidatorBuild :: new ( ) . struct_validate ( |_, s| {
20
+ if s. fields . len ( ) == 1 {
21
+ Ok ( ( ) )
22
+ } else {
23
+ Err ( s. span ( ) . error ( ONE_UNNAMED_FIELD ) )
24
+ }
25
+ } ) )
26
+ . outer_mapper ( MapperBuild :: new ( ) . struct_map ( |_, s| {
27
+ let pool_type = match & s. fields {
28
+ syn:: Fields :: Unnamed ( f) => & f. unnamed [ 0 ] . ty ,
29
+ _ => unreachable ! ( "Support::TupleStruct" ) ,
30
+ } ;
31
+
32
+ let decorated_type = & s. ident ;
33
+ let db_ty = quote_spanned ! ( decorated_type. span( ) =>
34
+ <#decorated_type as rocket_db_pools:: Database >
35
+ ) ;
36
+
37
+ quote_spanned ! { decorated_type. span( ) =>
38
+ impl From <#pool_type> for #decorated_type {
39
+ fn from( pool: #pool_type) -> Self {
40
+ Self ( pool)
45
41
}
42
+ }
46
43
47
- impl std:: ops:: Deref for #decorated_type {
48
- type Target = #pool_type;
44
+ impl std:: ops:: Deref for #decorated_type {
45
+ type Target = #pool_type;
49
46
50
- fn deref( & self ) -> & Self :: Target {
51
- & self . 0
52
- }
47
+ fn deref( & self ) -> & Self :: Target {
48
+ & self . 0
53
49
}
50
+ }
54
51
55
- impl std:: ops:: DerefMut for #decorated_type {
56
- fn deref_mut( & mut self ) -> & mut Self :: Target {
57
- & mut self . 0
58
- }
52
+ impl std:: ops:: DerefMut for #decorated_type {
53
+ fn deref_mut( & mut self ) -> & mut Self :: Target {
54
+ & mut self . 0
59
55
}
56
+ }
60
57
61
- #[ rocket:: async_trait]
62
- impl <' r> rocket:: request:: FromRequest <' r> for & ' r #decorated_type {
63
- type Error = ( ) ;
64
-
65
- async fn from_request(
66
- req: & ' r rocket:: request:: Request <' _>
67
- ) -> rocket:: request:: Outcome <Self , Self :: Error > {
68
- match #db_ty:: fetch( req. rocket( ) ) {
69
- Some ( db) => rocket:: outcome:: Outcome :: Success ( db) ,
70
- None => rocket:: outcome:: Outcome :: Failure ( (
71
- rocket:: http:: Status :: InternalServerError , ( ) ) )
72
- }
58
+ #[ rocket:: async_trait]
59
+ impl <' r> rocket:: request:: FromRequest <' r> for & ' r #decorated_type {
60
+ type Error = ( ) ;
61
+
62
+ async fn from_request(
63
+ req: & ' r rocket:: request:: Request <' _>
64
+ ) -> rocket:: request:: Outcome <Self , Self :: Error > {
65
+ match #db_ty:: fetch( req. rocket( ) ) {
66
+ Some ( db) => rocket:: outcome:: Outcome :: Success ( db) ,
67
+ None => rocket:: outcome:: Outcome :: Failure ( (
68
+ rocket:: http:: Status :: InternalServerError , ( ) ) )
73
69
}
74
70
}
71
+ }
75
72
76
- impl rocket:: Sentinel for & #decorated_type {
77
- fn abort( rocket: & rocket:: Rocket <rocket:: Ignite >) -> bool {
78
- #db_ty:: fetch( rocket) . is_none( )
79
- }
73
+ impl rocket:: Sentinel for & #decorated_type {
74
+ fn abort( rocket: & rocket:: Rocket <rocket:: Ignite >) -> bool {
75
+ #db_ty:: fetch( rocket) . is_none( )
80
76
}
81
77
}
82
- } )
83
- )
78
+ }
79
+ } ) )
84
80
. outer_mapper ( quote ! ( #[ rocket:: async_trait] ) )
85
- . inner_mapper ( MapperBuild :: new ( )
86
- . try_struct_map ( |_, s| {
87
- let db_name = DatabaseAttribute :: one_from_attrs ( "database" , & s. attrs ) ?
88
- . map ( |attr| attr. name )
89
- . ok_or_else ( || s. span ( ) . error ( ONE_DATABASE_ATTR ) ) ?;
81
+ . inner_mapper ( MapperBuild :: new ( ) . try_struct_map ( |_, s| {
82
+ let db_name = DatabaseAttribute :: one_from_attrs ( "database" , & s. attrs ) ?
83
+ . map ( |attr| attr. name )
84
+ . ok_or_else ( || s. span ( ) . error ( ONE_DATABASE_ATTR ) ) ?;
90
85
91
- let fairing_name = format ! ( "'{}' Database Pool" , db_name) ;
86
+ let fairing_name = format ! ( "'{}' Database Pool" , db_name) ;
92
87
93
- let pool_type = match & s. fields {
94
- syn:: Fields :: Unnamed ( f) => & f. unnamed [ 0 ] . ty ,
95
- _ => unreachable ! ( "Support::TupleStruct" ) ,
96
- } ;
88
+ let pool_type = match & s. fields {
89
+ syn:: Fields :: Unnamed ( f) => & f. unnamed [ 0 ] . ty ,
90
+ _ => unreachable ! ( "Support::TupleStruct" ) ,
91
+ } ;
97
92
98
- Ok ( quote_spanned ! { pool_type. span( ) =>
99
- type Pool = #pool_type;
93
+ Ok ( quote_spanned ! { pool_type. span( ) =>
94
+ type Pool = #pool_type;
100
95
101
- const NAME : & ' static str = #db_name;
96
+ const NAME : & ' static str = #db_name;
102
97
103
- fn init( ) -> rocket_db_pools:: Initializer <Self > {
104
- rocket_db_pools:: Initializer :: with_name( #fairing_name)
105
- }
106
- } )
98
+ fn init( ) -> rocket_db_pools:: Initializer <Self > {
99
+ rocket_db_pools:: Initializer :: with_name( #fairing_name)
100
+ }
107
101
} )
108
- )
102
+ } ) )
109
103
. to_tokens ( )
110
104
}
0 commit comments