🦀 Statum: Zero-Boilerplate Compile-Time State Machines in Rust
Hey Rustaceans! I've created a library for building type-safe state machines in Rust that makes state transitions impossible to get wrong at compile time.
Key Features
- 🛡️ Compile-time state transition validation
- 🔒 Type-safe state data access
- ⚡ Zero boilerplate implementation
- 📦 Simple, intuitive API
Quick Example
use statum::{state, machine};
#[state]
pub enum TaskState {
New,
InProgress,
Complete,
}
#[machine]
struct Task<S: TaskState> {
id: String,
name: String,
}
impl Task<New> {
fn start(self) -> Task<InProgress> {
self.transition()
}
}
impl Task<InProgress> {
fn complete(self) -> Task<Complete> {
self.transition()
}
}
fn main() {
let task = Task::new("task-1".to_owned(), "Important Task".to_owned())
.start()
.complete();
}
States with Data
Need to attach data to specific states? No problem:
#[state]
pub enum DocumentState {
Draft,
Review(ReviewData), // State with associated data
Published,
}
struct ReviewData {
reviewer: String,
comments: Vec<String>,
}
impl Document<Draft> {
fn submit_for_review(self, reviewer: String) -> Document<Review> {
self.transition_with(ReviewData {
reviewer,
comments: vec![],
})
}
}
Accessing State Data
When a state has associated data, you can access it safely:
impl Document<Review> {
fn add_comment(&mut self, comment: String) {
// Safely modify state data
if let Some(review_data) = self.get_state_data_mut() {
review_data.comments.push(comment);
}
}
fn get_reviewer(&self) -> Option<&str> {
// Safely read state data
self.get_state_data().map(|data| data.reviewer.as_str())
}
fn approve(self) -> Document<Published> {
// Transition to a state without data
self.transition()
}
}
Why Statum?
I created Statum because existing state machine libraries often require:
- Complex trait implementations
- Manual state transition validation
- Runtime checks for state data access
Statum moves all these checks to compile-time while keeping the API simple and ergonomic.
Looking for Feedback!
The crate is in active development, and I'd love to hear from the community:
- What state machine patterns do you commonly use?
- Are there specific features you'd like to see?
- Any suggestions for improving the API?
Try It Out
cargo add statum
GitHub: https://github.com/eboody/statum
Crates.io: https://crates.io/crates/statum
Let me know what you think! 🦀