11use darling:: FromMeta ;
22
3+ const MAGIC_METHOD : [ & ' static str ; 17 ] = [
4+ "__construct" ,
5+ "__destruct" ,
6+ "__call" ,
7+ "__call_static" ,
8+ "__get" ,
9+ "__set" ,
10+ "__isset" ,
11+ "__unset" ,
12+ "__sleep" ,
13+ "__wakeup" ,
14+ "__serialize" ,
15+ "__unserialize" ,
16+ "__to_string" ,
17+ "__invoke" ,
18+ "__set_state" ,
19+ "__clone" ,
20+ "__debug_info" ,
21+ ] ;
22+
323#[ derive( Debug , FromMeta ) ]
424pub enum Visibility {
525 #[ darling( rename = "public" ) ]
@@ -10,6 +30,24 @@ pub enum Visibility {
1030 Protected ,
1131}
1232
33+ pub trait IsMagic {
34+ fn is_magic ( & self ) -> bool ;
35+ }
36+
37+ impl IsMagic for & str {
38+ fn is_magic ( & self ) -> bool {
39+ MAGIC_METHOD . contains ( self )
40+ }
41+ }
42+
43+ pub trait Rename {
44+ fn rename ( & self , rule : & RenameRule ) -> String ;
45+ }
46+
47+ pub trait MethodRename : Rename {
48+ fn rename_method ( & self , rule : & RenameRule ) -> String ;
49+ }
50+
1351#[ derive( FromMeta , Debug , Default ) ]
1452#[ darling( default ) ]
1553pub struct PhpRename {
@@ -24,7 +62,7 @@ impl PhpRename {
2462 let name = name. as_ref ( ) ;
2563 self . rename
2664 . as_ref ( )
27- . map_or_else ( || name. to_string ( ) , |r| r . rename ( name ) )
65+ . map_or_else ( || name. to_string ( ) , |r| name . rename ( & r ) )
2866 } ,
2967 ToString :: to_string,
3068 )
@@ -51,50 +89,64 @@ pub enum RenameRule {
5189 ScreamingSnakeCase ,
5290}
5391
54- impl RenameRule {
55- /// Change case of an identifier.
56- ///
57- /// Magic methods are handled specially to make sure they're always cased
58- /// correctly.
59- pub fn rename ( self , name : impl AsRef < str > ) -> String {
60- let name = name. as_ref ( ) ;
61- match self {
62- RenameRule :: None => name. to_string ( ) ,
63- rule => match name {
64- "__construct" => "__construct" . to_string ( ) ,
65- "__destruct" => "__destruct" . to_string ( ) ,
66- "__call" => "__call" . to_string ( ) ,
67- "__call_static" => "__callStatic" . to_string ( ) ,
68- "__get" => "__get" . to_string ( ) ,
69- "__set" => "__set" . to_string ( ) ,
70- "__isset" => "__isset" . to_string ( ) ,
71- "__unset" => "__unset" . to_string ( ) ,
72- "__sleep" => "__sleep" . to_string ( ) ,
73- "__wakeup" => "__wakeup" . to_string ( ) ,
74- "__serialize" => "__serialize" . to_string ( ) ,
75- "__unserialize" => "__unserialize" . to_string ( ) ,
76- "__to_string" => "__toString" . to_string ( ) ,
77- "__invoke" => "__invoke" . to_string ( ) ,
78- "__set_state" => "__set_state" . to_string ( ) ,
79- "__clone" => "__clone" . to_string ( ) ,
80- "__debug_info" => "__debugInfo" . to_string ( ) ,
81- field => match rule {
82- Self :: Camel => ident_case:: RenameRule :: CamelCase . apply_to_field ( field) ,
83- Self :: Pascal => ident_case:: RenameRule :: PascalCase . apply_to_field ( field) ,
84- Self :: Snake => ident_case:: RenameRule :: SnakeCase . apply_to_field ( field) ,
85- Self :: ScreamingSnakeCase => {
86- ident_case:: RenameRule :: ScreamingSnakeCase . apply_to_field ( field)
87- }
88- Self :: None => unreachable ! ( ) ,
89- } ,
90- } ,
92+ impl Rename for & str {
93+ fn rename ( & self , rule : & RenameRule ) -> String {
94+ match * rule {
95+ RenameRule :: None => self . to_string ( ) ,
96+ RenameRule :: Camel => ident_case:: RenameRule :: CamelCase . apply_to_field ( self ) ,
97+ RenameRule :: Pascal => ident_case:: RenameRule :: PascalCase . apply_to_field ( self ) ,
98+ RenameRule :: Snake => ident_case:: RenameRule :: SnakeCase . apply_to_field ( self ) ,
99+ RenameRule :: ScreamingSnakeCase => {
100+ ident_case:: RenameRule :: ScreamingSnakeCase . apply_to_field ( self )
101+ }
102+ }
103+ }
104+ }
105+
106+ impl Rename for syn:: Ident {
107+ fn rename ( & self , rule : & RenameRule ) -> String {
108+ let s = self . to_string ( ) ;
109+ match * rule {
110+ RenameRule :: None => s,
111+ RenameRule :: Camel => ident_case:: RenameRule :: CamelCase . apply_to_field ( s. as_str ( ) ) ,
112+ RenameRule :: Pascal => ident_case:: RenameRule :: PascalCase . apply_to_field ( s. as_str ( ) ) ,
113+ RenameRule :: Snake => ident_case:: RenameRule :: SnakeCase . apply_to_field ( s. as_str ( ) ) ,
114+ RenameRule :: ScreamingSnakeCase => {
115+ ident_case:: RenameRule :: ScreamingSnakeCase . apply_to_field ( s. as_str ( ) )
116+ }
117+ }
118+ }
119+ }
120+
121+ impl MethodRename for syn:: Ident {
122+ fn rename_method ( & self , rule : & RenameRule ) -> String {
123+ let s = self . to_string ( ) ;
124+
125+ if MAGIC_METHOD . contains ( & s. as_str ( ) ) {
126+ s
127+ } else {
128+ self . rename ( rule)
129+ }
130+ }
131+ }
132+
133+ impl MethodRename for & str {
134+ fn rename_method ( & self , rule : & RenameRule ) -> String {
135+ let s = self . to_string ( ) ;
136+
137+ if MAGIC_METHOD . contains ( & s. as_str ( ) ) {
138+ s
139+ } else {
140+ self . rename ( rule)
91141 }
92142 }
93143}
94144
95145#[ cfg( test) ]
96146mod tests {
97- use super :: { PhpRename , RenameRule } ;
147+ use crate :: parsing:: { MethodRename , Rename } ;
148+
149+ use super :: { PhpRename , RenameRule , MAGIC_METHOD } ;
98150
99151 #[ test]
100152 fn test_php_rename ( ) {
@@ -133,44 +185,26 @@ mod tests {
133185
134186 #[ test]
135187 fn test_rename_magic ( ) {
136- for & ( magic, expected) in & [
137- ( "__construct" , "__construct" ) ,
138- ( "__destruct" , "__destruct" ) ,
139- ( "__call" , "__call" ) ,
140- ( "__call_static" , "__callStatic" ) ,
141- ( "__get" , "__get" ) ,
142- ( "__set" , "__set" ) ,
143- ( "__isset" , "__isset" ) ,
144- ( "__unset" , "__unset" ) ,
145- ( "__sleep" , "__sleep" ) ,
146- ( "__wakeup" , "__wakeup" ) ,
147- ( "__serialize" , "__serialize" ) ,
148- ( "__unserialize" , "__unserialize" ) ,
149- ( "__to_string" , "__toString" ) ,
150- ( "__invoke" , "__invoke" ) ,
151- ( "__set_state" , "__set_state" ) ,
152- ( "__clone" , "__clone" ) ,
153- ( "__debug_info" , "__debugInfo" ) ,
154- ] {
155- assert_eq ! ( magic, RenameRule :: None . rename( magic) ) ;
156- assert_eq ! ( expected, RenameRule :: Camel . rename( magic) ) ;
157- assert_eq ! ( expected, RenameRule :: Pascal . rename( magic) ) ;
158- assert_eq ! ( expected, RenameRule :: Snake . rename( magic) ) ;
159- assert_eq ! ( expected, RenameRule :: ScreamingSnakeCase . rename( magic) ) ;
188+ for magic in MAGIC_METHOD {
189+ assert_eq ! ( magic, magic. rename_method( & RenameRule :: None ) ) ;
190+ assert_eq ! ( magic, magic. rename_method( & RenameRule :: Camel ) ) ;
191+ assert_eq ! ( magic, magic. rename_method( & RenameRule :: Pascal ) ) ;
192+ assert_eq ! ( magic, magic. rename_method( & RenameRule :: Snake ) ) ;
193+ assert_eq ! ( magic, magic. rename_method( & RenameRule :: ScreamingSnakeCase ) ) ;
160194 }
161195 }
162196
163197 #[ test]
164198 fn test_rename_php_methods ( ) {
165199 let & ( original, camel, snake, pascal, screaming_snake) =
166200 & ( "get_name" , "getName" , "get_name" , "GetName" , "GET_NAME" ) ;
167- assert_eq ! ( original, RenameRule :: None . rename ( original ) ) ;
168- assert_eq ! ( camel, RenameRule :: Camel . rename ( original ) ) ;
169- assert_eq ! ( pascal, RenameRule :: Pascal . rename ( original ) ) ;
170- assert_eq ! ( snake, RenameRule :: Snake . rename ( original ) ) ;
201+ assert_eq ! ( original, original . rename ( & RenameRule :: None ) ) ;
202+ assert_eq ! ( camel, original . rename ( & RenameRule :: Camel ) ) ;
203+ assert_eq ! ( pascal, original . rename ( & RenameRule :: Pascal ) ) ;
204+ assert_eq ! ( snake, original . rename ( & RenameRule :: Snake ) ) ;
171205 assert_eq ! (
172206 screaming_snake,
173- RenameRule :: ScreamingSnakeCase . rename ( original )
207+ original . rename ( & RenameRule :: ScreamingSnakeCase )
174208 ) ;
175209 }
176210}
0 commit comments