rorm_macro_impl/
lib.rs

1//! This crate tries to follow the base layout proposed by a [ferrous-systems.com](https://ferrous-systems.com/blog/testing-proc-macros/#the-pipeline) blog post.
2
3use proc_macro2::TokenStream;
4use quote::quote;
5
6use crate::analyze::model::analyze_model;
7use crate::generate::db_enum::generate_db_enum;
8use crate::generate::model::generate_model;
9use crate::generate::patch::generate_patch;
10use crate::parse::db_enum::parse_db_enum;
11use crate::parse::model::parse_model;
12use crate::parse::patch::parse_patch;
13
14mod analyze;
15mod generate;
16mod parse;
17mod utils;
18
19/// Implementation of `rorm`'s `#[derive(DbEnum)]` macro
20pub fn derive_db_enum(input: TokenStream, config: MacroConfig) -> TokenStream {
21    match parse_db_enum(input) {
22        Ok(model) => generate_db_enum(&model, &config),
23        Err(error) => error.write_errors(),
24    }
25}
26
27/// Implementation of `rorm`'s `#[derive(Model)]` macro
28pub fn derive_model(input: TokenStream, config: MacroConfig) -> TokenStream {
29    match parse_model(input).and_then(analyze_model) {
30        Ok(model) => generate_model(&model, &config),
31        Err(error) => error.write_errors(),
32    }
33}
34
35/// Implementation of `rorm`'s `#[derive(Patch)]` macro
36pub fn derive_patch(input: TokenStream, config: MacroConfig) -> TokenStream {
37    match parse_patch(input) {
38        Ok(patch) => generate_patch(&patch, &config),
39        Err(error) => error.write_errors(),
40    }
41}
42
43/// Configuration for `rorm`'s macros
44///
45/// This struct can be useful for other crates wrapping `rorm`'s macros to tweak their behaviour.
46#[cfg_attr(doc, non_exhaustive)]
47pub struct MacroConfig {
48    /// Path to the `rorm` crate
49    ///
50    /// This path can be overwritten by another library which wraps and re-exports `rorm`.
51    ///
52    /// Defaults to `::rorm` which requires `rorm` to be a direct dependency
53    /// of any crate using `rorm`'s macros.
54    pub rorm_path: TokenStream,
55
56    #[cfg(not(doc))]
57    pub non_exhaustive: private::NonExhaustive,
58}
59
60mod private {
61    pub struct NonExhaustive;
62}
63
64impl Default for MacroConfig {
65    fn default() -> Self {
66        Self {
67            rorm_path: quote! { ::rorm },
68            non_exhaustive: private::NonExhaustive,
69        }
70    }
71}