Skip to content

Commit 5033ed0

Browse files
committed
docs(enum): extend enum documentation
Refs: #178
1 parent 39c11a8 commit 5033ed0

File tree

7 files changed

+178
-45
lines changed

7 files changed

+178
-45
lines changed

.lefthook.yml

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,8 @@ pre-commit:
1515
The `docsrs_bindings.rs` file seems to be out of date.
1616
Please check the updated bindings in `docsrs_bindings.rs` and commit the changes.
1717
- name: "macro docs"
18-
run: tools/update_lib_docs.sh && git diff --exit-code crates/macros/src/lib.rs
19-
glob: "guide/src/macros/*.md"
20-
fail_text: |
21-
The macro crates documentation seems to be out of date.
22-
Please check the updated documentation in `crates/macros/src/lib.rs` and commit the changes.
18+
run: tools/update_lib_docs.sh
19+
glob:
20+
- "guide/src/macros/*.md"
21+
- "crates/macros/src/lib.rs"
22+
stage_fixed: true

crates/macros/src/enum_.rs

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ struct PhpEnumAttribute {
2020
#[darling(default)]
2121
allow_native_discriminants: Flag,
2222
rename_cases: Option<RenameRule>,
23+
// TODO: Implement visibility support
2324
vis: Option<Visibility>,
2425
attrs: Vec<syn::Attribute>,
2526
}
@@ -30,8 +31,6 @@ struct PhpEnumVariantAttribute {
3031
#[darling(flatten)]
3132
rename: PhpRename,
3233
discriminant: Option<Lit>,
33-
// TODO: Implement doc support for enum variants
34-
#[allow(dead_code)]
3534
attrs: Vec<syn::Attribute>,
3635
}
3736

@@ -342,7 +341,6 @@ impl ToTokens for Enum<'_> {
342341

343342
#[derive(Debug)]
344343
struct EnumCase {
345-
#[allow(dead_code)]
346344
ident: Ident,
347345
name: String,
348346
#[allow(dead_code)]

crates/macros/src/lib.rs

Lines changed: 79 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -220,18 +220,28 @@ pub fn php_class(args: TokenStream, input: TokenStream) -> TokenStream {
220220
///
221221
/// Enums can be exported to PHP as enums with the `#[php_enum]` attribute
222222
/// macro. This attribute derives the `RegisteredClass` and `PhpEnum` traits on
223-
/// your enum. To register the enum use the `r#enum::<EnumName>()` method on the
224-
/// `ModuleBuilder` in the `#[php_module]` macro.
223+
/// your enum. To register the enum use the `enumeration::<EnumName>()` method
224+
/// on the `ModuleBuilder` in the `#[php_module]` macro.
225225
///
226226
/// ## Options
227227
///
228-
/// tbd
228+
/// The `#[php_enum]` attribute can be configured with the following options:
229+
/// - `#[php(name = "EnumName")]` or `#[php(change_case = snake_case)]`: Sets
230+
/// the name of the enum in PHP. The default is the `PascalCase` name of the
231+
/// enum.
232+
/// - `#[php(allow_native_discriminants)]`: Allows the use of native Rust
233+
/// discriminants (e.g., `Hearts = 1`).
229234
///
230-
/// ## Restrictions
231-
///
232-
/// tbd
235+
/// The cases of the enum can be configured with the following options:
236+
/// - `#[php(name = "CaseName")]` or `#[php(change_case = snake_case)]`: Sets
237+
/// the name of the enum case in PHP. The default is the `PascalCase` name of
238+
/// the case.
239+
/// - `#[php(discriminant = "value")]` or `#[php(discriminant = 123)]`: Sets the
240+
/// discriminant value for the enum case. This can be a string or an integer.
241+
/// If not set, the case will be exported as a simple enum case without a
242+
/// discriminant.
233243
///
234-
/// ## Example
244+
/// ### Example
235245
///
236246
/// This example creates a PHP enum `Suit`.
237247
///
@@ -250,11 +260,72 @@ pub fn php_class(args: TokenStream, input: TokenStream) -> TokenStream {
250260
///
251261
/// #[php_module]
252262
/// pub fn get_module(module: ModuleBuilder) -> ModuleBuilder {
253-
/// module.r#enum::<Suit>()
263+
/// module.enumeration::<Suit>()
254264
/// }
255265
/// # fn main() {}
256266
/// ```
257267
///
268+
/// ## Backed Enums
269+
/// Enums can also be backed by either `i64` or `&'static str`. Those values can
270+
/// be set using the `#[php(discriminant = "value")]` or `#[php(discriminant =
271+
/// 123)]` attributes on the enum variants.
272+
///
273+
/// All variants must have a discriminant of the same type, either all `i64` or
274+
/// all `&'static str`.
275+
///
276+
/// ```rust,no_run,ignore
277+
/// # #![cfg_attr(windows, feature(abi_vectorcall))]
278+
/// # extern crate ext_php_rs;
279+
/// use ext_php_rs::prelude::*;
280+
///
281+
/// #[php_enum]
282+
/// pub enum Suit {
283+
/// #[php(discriminant = "hearts")]
284+
/// Hearts,
285+
/// #[php(discriminant = "diamonds")]
286+
/// Diamonds,
287+
/// #[php(discriminant = "clubs")]
288+
/// Clubs,
289+
/// #[php(discriminant = "spades")]
290+
/// Spades,
291+
/// }
292+
/// #[php_module]
293+
/// pub fn get_module(module: ModuleBuilder) -> ModuleBuilder {
294+
/// module.enumeration::<Suit>()
295+
/// }
296+
/// # fn main() {}
297+
/// ```
298+
///
299+
/// ### 'Native' Discriminators
300+
/// Native rust discriminants are currently not supported and will not be
301+
/// exported to PHP.
302+
///
303+
/// To avoid confusion a compiler error will be raised if you try to use a
304+
/// native discriminant. You can ignore this error by adding the
305+
/// `#[php(allow_native_discriminants)]` attribute to your enum.
306+
///
307+
/// ```rust,no_run,ignore
308+
/// # #![cfg_attr(windows, feature(abi_vectorcall))]
309+
/// # extern crate ext_php_rs;
310+
/// use ext_php_rs::prelude::*;
311+
///
312+
/// #[php_enum]
313+
/// #[php(allow_native_discriminants)]
314+
/// pub enum Suit {
315+
/// Hearts = 1,
316+
/// Diamonds = 2,
317+
/// Clubs = 3,
318+
/// Spades = 4,
319+
/// }
320+
///
321+
/// #[php_module]
322+
/// pub fn get_module(module: ModuleBuilder) -> ModuleBuilder {
323+
/// module.enumeration::<Suit>()
324+
/// }
325+
/// # fn main() {}
326+
/// ```
327+
///
328+
///
258329
/// TODO: Add backed enums example
259330
// END DOCS FROM enum.md
260331
#[proc_macro_attribute]

guide/src/macros/enum.md

Lines changed: 69 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2,18 +2,23 @@
22

33
Enums can be exported to PHP as enums with the `#[php_enum]` attribute macro.
44
This attribute derives the `RegisteredClass` and `PhpEnum` traits on your enum.
5-
To register the enum use the `r#enum::<EnumName>()` method on the `ModuleBuilder`
5+
To register the enum use the `enumeration::<EnumName>()` method on the `ModuleBuilder`
66
in the `#[php_module]` macro.
77

88
## Options
99

10-
tbd
10+
The `#[php_enum]` attribute can be configured with the following options:
11+
- `#[php(name = "EnumName")]` or `#[php(change_case = snake_case)]`: Sets the name of the enum in PHP.
12+
The default is the `PascalCase` name of the enum.
13+
- `#[php(allow_native_discriminants)]`: Allows the use of native Rust discriminants (e.g., `Hearts = 1`).
1114

12-
## Restrictions
15+
The cases of the enum can be configured with the following options:
16+
- `#[php(name = "CaseName")]` or `#[php(change_case = snake_case)]`: Sets the name of the enum case in PHP.
17+
The default is the `PascalCase` name of the case.
18+
- `#[php(discriminant = "value")]` or `#[php(discriminant = 123)]`: Sets the discriminant value for the enum case.
19+
This can be a string or an integer. If not set, the case will be exported as a simple enum case without a discriminant.
1320

14-
tbd
15-
16-
## Example
21+
### Example
1722

1823
This example creates a PHP enum `Suit`.
1924

@@ -32,9 +37,66 @@ pub enum Suit {
3237
3338
#[php_module]
3439
pub fn get_module(module: ModuleBuilder) -> ModuleBuilder {
35-
module.r#enum::<Suit>()
40+
module.enumeration::<Suit>()
3641
}
3742
# fn main() {}
3843
```
3944

45+
## Backed Enums
46+
Enums can also be backed by either `i64` or `&'static str`. Those values can be set using the
47+
`#[php(discriminant = "value")]` or `#[php(discriminant = 123)]` attributes on the enum variants.
48+
49+
All variants must have a discriminant of the same type, either all `i64` or all `&'static str`.
50+
51+
```rust,no_run
52+
# #![cfg_attr(windows, feature(abi_vectorcall))]
53+
# extern crate ext_php_rs;
54+
use ext_php_rs::prelude::*;
55+
56+
#[php_enum]
57+
pub enum Suit {
58+
#[php(discriminant = "hearts")]
59+
Hearts,
60+
#[php(discriminant = "diamonds")]
61+
Diamonds,
62+
#[php(discriminant = "clubs")]
63+
Clubs,
64+
#[php(discriminant = "spades")]
65+
Spades,
66+
}
67+
#[php_module]
68+
pub fn get_module(module: ModuleBuilder) -> ModuleBuilder {
69+
module.enumeration::<Suit>()
70+
}
71+
# fn main() {}
72+
```
73+
74+
### 'Native' Discriminators
75+
Native rust discriminants are currently not supported and will not be exported to PHP.
76+
77+
To avoid confusion a compiler error will be raised if you try to use a native discriminant.
78+
You can ignore this error by adding the `#[php(allow_native_discriminants)]` attribute to your enum.
79+
80+
```rust,no_run
81+
# #![cfg_attr(windows, feature(abi_vectorcall))]
82+
# extern crate ext_php_rs;
83+
use ext_php_rs::prelude::*;
84+
85+
#[php_enum]
86+
#[php(allow_native_discriminants)]
87+
pub enum Suit {
88+
Hearts = 1,
89+
Diamonds = 2,
90+
Clubs = 3,
91+
Spades = 4,
92+
}
93+
94+
#[php_module]
95+
pub fn get_module(module: ModuleBuilder) -> ModuleBuilder {
96+
module.enumeration::<Suit>()
97+
}
98+
# fn main() {}
99+
```
100+
101+
40102
TODO: Add backed enums example

guide/src/macros/php.md

Lines changed: 20 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -33,24 +33,26 @@ fn hello_world(a: i32, b: i32) -> i32 {
3333

3434
Which attributes are available depends on the element you are annotating:
3535

36-
| Attribute | `const` | `fn` | `struct` | `struct` field | `impl` | `impl` `const` | `impl` `fn` |
37-
| -------------------- | ------- | ---- | -------- | -------------- | ------ | -------------- | ----------- |
38-
| name ||||||||
39-
| change_case ||||||||
40-
| change_method_case ||||||||
41-
| change_constant_case ||||||||
42-
| flags ||||||||
43-
| prop ||||||||
44-
| extends ||||||||
45-
| implements ||||||||
46-
| modifier ||||||||
47-
| defaults ||||||||
48-
| optional ||||||||
49-
| vis ||||||||
50-
| getter ||||||||
51-
| setter ||||||||
52-
| constructor ||||||||
53-
| abstract_method ||||||||
36+
| Attribute | `const` | `fn` | `struct` | `struct` field | `impl` | `impl` `const` | `impl` `fn` | `enum` | `enum` case |
37+
| -------------------------- | ------- | ---- | -------- | -------------- | ------ | -------------- | ----------- | ------ | ----------- |
38+
| name ||||||||||
39+
| change_case ||||||||||
40+
| change_method_case ||||||||||
41+
| change_constant_case ||||||||||
42+
| flags ||||||||||
43+
| prop ||||||||||
44+
| extends ||||||||||
45+
| implements ||||||||||
46+
| modifier ||||||||||
47+
| defaults ||||||||||
48+
| optional ||||||||||
49+
| vis ||||||||||
50+
| getter ||||||||||
51+
| setter ||||||||||
52+
| constructor ||||||||||
53+
| abstract_method ||||||||||
54+
| allow_native_discriminants ||||||||||
55+
| discriminant ||||||||||
5456

5557
## `name` and `change_case`
5658

src/builders/module.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -213,7 +213,7 @@ impl ModuleBuilder<'_> {
213213

214214
/// Adds an enum to the extension.
215215
#[cfg(feature = "enum")]
216-
pub fn r#enum<T>(mut self) -> Self
216+
pub fn enumeration<T>(mut self) -> Self
217217
where
218218
T: RegisteredClass + RegisteredEnum,
219219
{

tests/src/integration/enum_/mod.rs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -40,9 +40,9 @@ pub fn test_enum(a: TestEnum) -> Result<StringBackedEnum> {
4040

4141
pub fn build_module(builder: ModuleBuilder) -> ModuleBuilder {
4242
builder
43-
.r#enum::<TestEnum>()
44-
.r#enum::<IntBackedEnum>()
45-
.r#enum::<StringBackedEnum>()
43+
.enumeration::<TestEnum>()
44+
.enumeration::<IntBackedEnum>()
45+
.enumeration::<StringBackedEnum>()
4646
.function(wrap_function!(test_enum))
4747
}
4848

0 commit comments

Comments
 (0)