botx-api-framework 0.1.8

Фреймворк для реализации ботов под платформу eXpress
Documentation
use std::any::TypeId;

use anthill_di::{
    DependencyContext,
    LifeCycle,
    types::*,
    ServiceMappingBuilder,
    Constructor
};
use async_lock::RwLock;
use easy_ext::ext;
use regex::Regex;

use crate::{handlers::{
    command::*,
    button::*,
    internal_bot_notification::*,
    message::*,
    added_to_chat::*,
    chat_created::*,
    chat_deleted_by_user::*,
    cts_login::*,
    cts_logout::*,
    deleted_from_chat::*,
    left_from_chat::*,
    smartapp_event::*,
    status::*,
    notification_result::*,
    edit_event::*,
    },
    contexts::{
        BotXApiFrameworkContext,
        NotificationContext
    }
};


#[ext(IAnthillDiExt)]
#[async_trait_with_sync::async_trait]
pub impl DependencyContext {
    async fn register_command_detection_regex(&self, regex: Regex) -> AddDependencyResult<ServiceMappingBuilder<CommandDetectionRegex>> {
        self.register_closure::<CommandDetectionRegex, _>(
                move |_| Ok(regex.clone().into()),
                LifeCycle::Transient,
            )
            .await
    }

    async fn register_command_handler<THandler: ICommandHandler + Constructor + 'static>(&self, command_regex: Regex)
        -> MapComponentResult<ServiceMappingBuilder<THandler>>
    {
        self.register_closure(move |_| Ok(CommandHandlerMatchingRule::<THandler> {
                command_regex: command_regex.clone().into(),
                pd: Default::default(),
            }),
            LifeCycle::Transient).await.unwrap()
            .map_as::<dyn ICommandHandlerMatchingRule>().await?;

        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn ICommandHandler>()
            .await
    }

    async fn register_default_command_handler<THandler: ICommandHandler + 'static>(&self) -> AddDependencyResult<ServiceMappingBuilder<DefaultCommandHandlerId>> {
        self.register_closure::<DefaultCommandHandlerId, _>(
                |_| Ok(DefaultCommandHandlerId(TypeId::of::<THandler>())),
                LifeCycle::Transient

            ).await
    }

    async fn register_message_handler<THandler: IMessageHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IMessageHandler>()
            .await
    }

    async fn register_button_handler<THandler: IButtonHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {
        self.register_type::<ButtonHandlerMatchingRule<THandler>>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IButtonHandlerMatchingRule>()
            .await?;

        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IButtonHandlerCallProducer>()
            .await
    }

    async fn register_default_button_handler<THandler: IButtonHandler<TData = serde_json::Value, TMetaData = serde_json::Value> + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IButtonHandler<TData = serde_json::Value, TMetaData = serde_json::Value>>()
            .await
    }

    async fn register_internal_notification_handler<THandler: IInternalBotNotificationHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {
        self.register_type::<InternalBotNotificationDataProcessor<THandler>>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IInternalBotNotificationDataProcessor>()
            .await?;
        
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IInternalBotNotificationCallProducer>()
            .await
    }

    async fn register_default_internal_notification_handler<THandler: IInternalBotNotificationHandler<TData = serde_json::Value, TOptions = serde_json::Value> + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IInternalBotNotificationHandler<TData = serde_json::Value, TOptions = serde_json::Value>>().await
    }

    async fn register_smartapp_event_handler<THandler: ISmartappEventHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {
        self.register_type::<SmartappEventDataProcessor<THandler>>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn ISmartappEventDataProcessor>()
            .await?;
        
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn ISmartappEventCallProducer>()
            .await
    }

    async fn register_default_smartapp_event_handler<THandler: ISmartappEventHandler<TData = serde_json::Value, TOptions = serde_json::Value> + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn ISmartappEventHandler<TData = serde_json::Value, TOptions = serde_json::Value>>().await
    }

    async fn register_add_to_chat_handler<THandler: IAddedToChatHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IAddedToChatHandler>().await
    }

    async fn register_chat_created_handler<THandler: IChatCreatedHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IChatCreatedHandler>().await
    }

    async fn register_chat_deleted_by_user_handler<THandler: IChatDeletedByUserHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IChatDeletedByUserHandler>().await
    }

    async fn register_cts_login_handler<THandler: ICtsLoginHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn ICtsLoginHandler>().await
    }

    async fn register_cts_logout_handler<THandler: ICtsLogoutHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn ICtsLogoutHandler>().await
    }

    async fn register_delete_from_chat_handler<THandler: IDeletedFromChatHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IDeletedFromChatHandler>().await
    }

    async fn register_left_from_chat_handler<THandler: ILeftFromChatHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn ILeftFromChatHandler>().await
    }

    async fn register_event_edit_handler<THandler: IEventEditHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {   
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IEventEditHandler>().await
    }

    async fn register_botx_api_framework_context(&self) -> AddDependencyResult<ServiceMappingBuilder<BotXApiFrameworkContext>> {
        self.register_type::<BotXApiFrameworkContext>(LifeCycle::Transient).await
    }

    async fn register_notification_callback_handler<THandler: INotificationResultHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn INotificationResultHandler>().await
    }

    async fn register_status_handler<THandler: IStatusHandler + Constructor + 'static>(&self) -> MapComponentResult<ServiceMappingBuilder<THandler>> {
        self.register_type::<THandler>(LifeCycle::Transient)
            .await
            .unwrap()
            .map_as::<dyn IStatusHandler>().await
    }

    async fn register_notification_context(&self) -> AddDependencyResult<ServiceMappingBuilder<RwLock<NotificationContext>>> {
        self.register_type::<NotificationContext>(LifeCycle::Transient)
            .await.unwrap();
        let ctx = self.resolve::<NotificationContext>().await.unwrap();
        self.register_instance(RwLock::new(ctx)).await
    }
}