Skip to main content

ironstate_derive/
lib.rs

1#![doc(
2    html_logo_url = "https://raw.githubusercontent.com/kassian-dev/ironstate/main/assets/logo.png",
3    html_favicon_url = "https://raw.githubusercontent.com/kassian-dev/ironstate/main/assets/favicon-32.png"
4)]
5//! Derive macros for [`ironstate`](https://docs.rs/ironstate).
6//!
7//! - `#[derive(StateMachine)]` generates the structural metadata a machine
8//!   needs: its initial state, terminal states, per-state event-kind
9//!   restrictions, and (with `version`/`history`) versioned restore.
10//! - `#[derive(Event)]` reads `#[event_kind]` and `#[likelihood]` and generates
11//!   the event metadata the runtime and verification macros consume.
12
13use proc_macro::TokenStream;
14use syn::{DeriveInput, parse_macro_input};
15
16mod common;
17mod event;
18mod statemachine;
19
20/// Derive `StateMachine` for an enum of states.
21///
22/// ```ignore
23/// #[derive(StateMachine, Clone, Debug, PartialEq)]
24/// #[state_machine(initial = Draft, terminal = [Published, Archived])]
25/// enum Article { Draft, Review, Published, Archived }
26/// ```
27#[proc_macro_derive(StateMachine, attributes(state_machine, only_accepts))]
28pub fn derive_state_machine(input: TokenStream) -> TokenStream {
29    let input = parse_macro_input!(input as DeriveInput);
30    statemachine::derive(input)
31        .unwrap_or_else(syn::Error::into_compile_error)
32        .into()
33}
34
35/// Derive `Event` for an enum of events.
36///
37/// ```ignore
38/// #[derive(Event, Clone, Debug, PartialEq)]
39/// enum Edit {
40///     Submit,
41///     #[event_kind = "operator"]
42///     Approve,
43///     #[likelihood = "rare"]
44///     Reject,
45/// }
46/// ```
47#[proc_macro_derive(Event, attributes(event_kind, likelihood))]
48pub fn derive_event(input: TokenStream) -> TokenStream {
49    let input = parse_macro_input!(input as DeriveInput);
50    event::derive(input)
51        .unwrap_or_else(syn::Error::into_compile_error)
52        .into()
53}