pub(crate) fn generate_reactor_types(def: &ReactorDefinition) -> TokenStream {
    let reactor_ident = def.reactor_ident();
    let event_ident = suffix_ident(&reactor_ident, "Event");
    let error_ident = suffix_ident(&reactor_ident, "Error");

    let mut event_variants = Vec::new();
    let mut error_variants = Vec::new();
    let mut display_variants = Vec::new();
    let mut error_display_variants = Vec::new();
    let mut error_source_variants = Vec::new();
    let mut from_impls = Vec::new();

    for component in def.components() {
        let variant_ident = component.variant_ident();
        let full_event_type = def.component_event(component);
        let full_error_type = component.full_error_type(quote!(#event_ident));
        let field_name = component.field_ident().to_string();

        let event_variant_doc = format!("Event from `{}` component", field_name);
        event_variants.push(quote!(
            #[doc = #event_variant_doc]
            #variant_ident(#full_event_type)));

        let error_variant_doc = format!("Error constructing `{}` component", field_name);
        error_variants.push(quote!(
            #[doc = #error_variant_doc]
            #variant_ident(#full_error_type)));

        display_variants.push(quote!(
            #event_ident::#variant_ident(inner) => write!(f, "{}: {}", #field_name, inner)
        ));

        error_display_variants.push(quote!(
            #error_ident::#variant_ident(inner) => write!(f, "{}: {}", #field_name, inner)
        ));

        error_source_variants.push(quote!(
            #error_ident::#variant_ident(inner) => Some(inner)
        ));

        from_impls.push(quote!(
            impl From<#full_event_type> for #event_ident {
                fn from(event: #full_event_type) -> Self {
                    #event_ident::#variant_ident(event)
                }
            }
        ));
    }

    // NOTE: Cannot use `From::from` to directly construct next component's event because doing so
    //       prevents us from implementing discards.

    // Add a variant for each request and a `From` implementation.
    for request in def.requests() {
        let variant_ident = request.variant_ident();
        let full_request_type = request.full_request_type();

        let event_variant_doc = format!("Incoming `{}`", variant_ident);
        event_variants.push(quote!(
            #[doc = #event_variant_doc]
            #variant_ident(#full_request_type)));

        display_variants.push(quote!(
           #event_ident::#variant_ident(inner) => ::std::fmt::Display::fmt(inner, f)
        ));

        from_impls.push(quote!(
            impl From<#full_request_type> for #event_ident {
                fn from(request: #full_request_type) -> Self {
                    #event_ident::#variant_ident(request)
                }
            }
        ));
    }

    for announcement in def.announcements() {
        let variant_ident = announcement.variant_ident();
        let full_announcement_type = announcement.full_announcement_type();

        let event_variant_doc = format!("Incoming `{}`", variant_ident);
        event_variants.push(quote!(
             #[doc = #event_variant_doc]
             #variant_ident(#full_announcement_type)));

        display_variants.push(quote!(
           #event_ident::#variant_ident(inner) => ::std::fmt::Display::fmt(inner, f)
        ));

        from_impls.push(quote!(
            impl From<#full_announcement_type> for #event_ident {
                fn from(announcement: #full_announcement_type) -> Self {
                    #event_ident::#variant_ident(announcement)
                }
            }
        ));
    }

    let event_docs = format!("Events of `{}` reactor.", reactor_ident);
    let error_docs = format!("Construction errors of `{}` reactor.", reactor_ident);

    quote!(
        #[doc = #event_docs]
        #[allow(clippy::large_enum_variant)]
        #[derive(Debug, serde::Serialize)]
        pub(crate) enum #event_ident {
           #(#event_variants,)*
        }

        impl crate::reactor::ReactorEvent for #event_ident {
            fn as_control(&self) -> Option<&crate::effect::announcements::ControlAnnouncement> {
                if let #event_ident::ControlAnnouncement(ref ctrl_ann) = self {
                    Some(ctrl_ann)
                } else {
                    None
                }
            }
        }

        #[doc = #error_docs]
        #[derive(Debug)]
        pub(crate) enum #error_ident {
            #(#error_variants,)*
            /// Failure to initialize metrics.
            MetricsInitialization(prometheus::Error),
        }

        impl std::fmt::Display for #event_ident {
            fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
                match self {
                    #(#display_variants,)*
                }
            }
        }

        impl std::fmt::Display for #error_ident {
            fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
                match self {
                    #(#error_display_variants,)*
                    #error_ident::MetricsInitialization(err) => write!(f, "metrics_initialization: {}", err),
                }
            }
        }

        #(#from_impls)*

        impl From<prometheus::Error> for #error_ident {
            fn from(err: prometheus::Error) -> Self {
                #error_ident::MetricsInitialization(err)
            }
        }

        impl std::error::Error for #error_ident {
            fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
                match self {
                    #(#error_source_variants,)*
                    #error_ident::MetricsInitialization(inner) => Some(inner),
                }
            }
        }
    )
}
/// Generates types for the reactor implementation.
Generates types for the reactor implementation.
Generates types for the reactor implementation .
pub(crate) fn generate_reactor_types(def: &ReactorDefinition) -> TokenStream {
    let reactor_ident = def.reactor_ident();
    let event_ident = suffix_ident(&reactor_ident, "Event");
    let error_ident = suffix_ident(&reactor_ident, "Error");
    let mut event_variants = Vec::new();
    let mut error_variants = Vec::new();
    let mut display_variants = Vec::new();
    let mut error_display_variants = Vec::new();
    let mut error_source_variants = Vec::new();
    let mut from_impls = Vec::new();
    for component in def.components() {
        let variant_ident = component.variant_ident();
        let full_event_type = def.component_event(component);
        let full_error_type = component.full_error_type(quote!(#event_ident));
        let field_name = component.field_ident().to_string();
        let event_variant_doc = format!("Event from `{}` component", field_name);
        event_variants.push(quote!(
            #[doc = #event_variant_doc]
            #variant_ident(#full_event_type)));
        let error_variant_doc = format!("Error constructing `{}` component", field_name);
        error_variants.push(quote!(
            #[doc = #error_variant_doc]
            #variant_ident(#full_error_type)));
        display_variants.push(quote!(
            #event_ident::#variant_ident(inner) => write!(f, "{}: {}", #field_name, inner)
        ));
        error_display_variants.push(quote!(
            #error_ident::#variant_ident(inner) => write!(f, "{}: {}", #field_name, inner)
        ));
        error_source_variants.push(quote!(
            #error_ident::#variant_ident(inner) => Some(inner)
        ));
        from_impls.push(quote!(
            impl From<#full_event_type> for #event_ident {
                fn from(event: #full_event_type) -> Self {
                    #event_ident::#variant_ident(event)
                }
            }
        ));
    }
    // NOTE: Cannot use `From::from` to directly construct next component's event because doing so
    //       prevents us from implementing discards.
    // Add a variant for each request and a `From` implementation.
    for request in def.requests() {
        let variant_ident = request.variant_ident();
        let full_request_type = request.full_request_type();
        let event_variant_doc = format!("Incoming `{}`", variant_ident);
        event_variants.push(quote!(
            #[doc = #event_variant_doc]
            #variant_ident(#full_request_type)));
        display_variants.push(quote!(
           #event_ident::#variant_ident(inner) => ::std::fmt::Display::fmt(inner, f)
        ));
        from_impls.push(quote!(
            impl From<#full_request_type> for #event_ident {
                fn from(request: #full_request_type) -> Self {
                    #event_ident::#variant_ident(request)
                }
            }
        ));
    }
    for announcement in def.announcements() {
        let variant_ident = announcement.variant_ident();
        let full_announcement_type = announcement.full_announcement_type();
        let event_variant_doc = format!("Incoming `{}`", variant_ident);
        event_variants.push(quote!(
             #[doc = #event_variant_doc]
             #variant_ident(#full_announcement_type)));
        display_variants.push(quote!(
           #event_ident::#variant_ident(inner) => ::std::fmt::Display::fmt(inner, f)
        ));
        from_impls.push(quote!(
            impl From<#full_announcement_type> for #event_ident {
                fn from(announcement: #full_announcement_type) -> Self {
                    #event_ident::#variant_ident(announcement)
                }
            }
        ));
    }
    let event_docs = format!("Events of `{}` reactor.", reactor_ident);
    let error_docs = format!("Construction errors of `{}` reactor.", reactor_ident);
    quote!(
        #[doc = #event_docs]
        #[allow(clippy::large_enum_variant)]
        #[derive(Debug, serde::Serialize)]
        pub(crate) enum #event_ident {
           #(#event_variants,)*
        }
        impl crate::reactor::ReactorEvent for #event_ident {
            fn as_control(&self) -> Option<&crate::effect::announcements::ControlAnnouncement> {
                if let #event_ident::ControlAnnouncement(ref ctrl_ann) = self {
                    Some(ctrl_ann)
                } else {
                    None
                }
            }
        }
        #[doc = #error_docs]
        #[derive(Debug)]
        pub(crate) enum #error_ident {
            #(#error_variants,)*
            /// Failure to initialize metrics.
            MetricsInitialization(prometheus::Error),
        }
        impl std::fmt::Display for #event_ident {
            fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
                match self {
                    #(#display_variants,)*
                }
            }
        }
        impl std::fmt::Display for #error_ident {
            fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
                match self {
                    #(#error_display_variants,)*
                    #error_ident::MetricsInitialization(err) => write!(f, "metrics_initialization: {}", err),
                }
            }
        }
        #(#from_impls)*
        impl From<prometheus::Error> for #error_ident {
            fn from(err: prometheus::Error) -> Self {
                #error_ident::MetricsInitialization(err)
            }
        }
        impl std::error::Error for #error_ident {
            fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
                match self {
                    #(#error_source_variants,)*
                    #error_ident::MetricsInitialization(inner) => Some(inner),
                }
            }
        }
    )
}
pub ( crate ) fn generate_reactor_types ( def : & ReactorDefinition ) -> TokenStream { let reactor_ident = def . reactor_ident ( ) ; let event_ident = suffix_ident ( & reactor_ident , " " ) ; let error_ident = suffix_ident ( & reactor_ident , " " ) ; let mut event_variants = Vec :: new ( ) ; let mut error_variants = Vec :: new ( ) ; let mut display_variants = Vec :: new ( ) ; let mut error_display_variants = Vec :: new ( ) ; let mut error_source_variants = Vec :: new ( ) ; let mut from_impls = Vec :: new ( ) ; for component in def . components ( ) { let variant_ident = component . variant_ident ( ) ; let full_event_type = def . component_event ( component ) ; let full_error_type = component . full_error_type ( quote ! ( event_ident ) ) ; let field_name = component . field_ident ( ) . to_string ( ) ; let event_variant_doc = format ! ( " " field_name ) ; event_variants . push ( quote ! ( [ doc event_variant_doc ] variant_ident ( full_event_type ) ) ) ; let error_variant_doc = format ! ( " " field_name ) ; error_variants . push ( quote ! ( [ doc error_variant_doc ] variant_ident ( full_error_type ) ) ) ; display_variants . push ( quote ! ( event_ident variant_ident ( inner ) write ( f " " field_name inner ) ) ) ; error_display_variants . push ( quote ! ( error_ident variant_ident ( inner ) write ( f " " field_name inner ) ) ) ; error_source_variants . push ( quote ! ( error_ident variant_ident ( inner ) Some ( inner ) ) ) ; from_impls . push ( quote ! ( impl From full_event_type for event_ident { fn from ( event full_event_type ) Self { event_ident variant_ident ( event ) } } ) ) ; } // NOTE: Cannot use `From::from` to directly construct next component's event because doing so //       prevents us from implementing discards. // Add a variant for each request and a `From` implementation. for request in def . requests ( ) { let variant_ident = request . variant_ident ( ) ; let full_request_type = request . full_request_type ( ) ; let event_variant_doc = format ! ( " " variant_ident ) ; event_variants . push ( quote ! ( [ doc event_variant_doc ] variant_ident ( full_request_type ) ) ) ; display_variants . push ( quote ! ( event_ident variant_ident ( inner ) std fmt Display fmt ( inner f ) ) ) ; from_impls . push ( quote ! ( impl From full_request_type for event_ident { fn from ( request full_request_type ) Self { event_ident variant_ident ( request ) } } ) ) ; } for announcement in def . announcements ( ) { let variant_ident = announcement . variant_ident ( ) ; let full_announcement_type = announcement . full_announcement_type ( ) ; let event_variant_doc = format ! ( " " variant_ident ) ; event_variants . push ( quote ! ( [ doc event_variant_doc ] variant_ident ( full_announcement_type ) ) ) ; display_variants . push ( quote ! ( event_ident variant_ident ( inner ) std fmt Display fmt ( inner f ) ) ) ; from_impls . push ( quote ! ( impl From full_announcement_type for event_ident { fn from ( announcement full_announcement_type ) Self { event_ident variant_ident ( announcement ) } } ) ) ; } let event_docs = format ! ( " " reactor_ident ) ; let error_docs = format ! ( " " reactor_ident ) ; quote ! ( [ doc event_docs ] [ allow ( clippy large_enum_variant ) ] [ derive ( Debug serde Serialize ) ] pub ( crate ) enum event_ident { ( event_variants ) } impl crate reactor ReactorEvent for event_ident { fn as_control ( self ) Option crate effect announcements ControlAnnouncement { if let event_ident ControlAnnouncement ( ref ctrl_ann ) self { Some ( ctrl_ann ) } else { None } } } [ doc error_docs ] [ derive ( Debug ) ] pub ( crate ) enum error_ident { ( error_variants ) /// Failure to initialize metrics. MetricsInitialization ( prometheus Error ) } impl std fmt Display for event_ident { fn fmt ( self f mut std fmt Formatter ' ) std fmt Result { match self { ( display_variants ) } } } impl std fmt Display for error_ident { fn fmt ( self f mut std fmt Formatter ' ) std fmt Result { match self { ( error_display_variants ) error_ident MetricsInitialization ( err ) write ( f " " err ) } } } ( from_impls ) impl From prometheus Error for error_ident { fn from ( err prometheus Error ) Self { error_ident MetricsInitialization ( err ) } } impl std error Error for error_ident { fn source ( self ) Option ( dyn std error Error ' static ) { match self { ( error_source_variants ) error_ident MetricsInitialization ( inner ) Some ( inner ) } } } ) }
Generates types for the reactor implementation.
Generates types for the reactor implementation .
def
&ReactorDefinition
def
&ReactorDefinition