infrarust 1.1.0

A Rust adaptation of the Infrared Minecraft proxy
Documentation
use log::{debug, error};
use std::sync::Arc;
use tokio::sync::mpsc::{Receiver, Sender};

use crate::core::{config::service::ConfigurationService, event::ProviderMessage};

pub mod file;

#[async_trait::async_trait]
pub trait Provider: Send {
    async fn run(&mut self);
    fn get_name(&self) -> String;
    fn new(config_sender: Sender<ProviderMessage>) -> Self
    where
        Self: Sized;
}

pub struct ConfigProvider {
    _providers: Vec<Box<dyn Provider>>,
    config_service: Arc<ConfigurationService>,
    provider_receiver: Receiver<ProviderMessage>,
    provider_sender: Sender<ProviderMessage>,
}

impl ConfigProvider {
    pub fn new(
        config_service: Arc<ConfigurationService>,
        provider_receiver: Receiver<ProviderMessage>,
        provider_sender: Sender<ProviderMessage>,
    ) -> Self {
        Self {
            _providers: vec![],
            config_service,
            provider_receiver,
            provider_sender,
        }
    }

    pub async fn run(&mut self) {
        debug!("Starting ConfigProvider(run)");
        while let Some(message) = self.provider_receiver.recv().await {
            debug!("Received message in ConfigProvider(run): {:?}", message);
            match message {
                ProviderMessage::Update { key, configuration } => {
                    debug!("Configuration update received for key: {}", key);
                    match configuration {
                        Some(config) => {
                            self.config_service
                                .update_configurations(vec![*config])
                                .await;
                        }
                        None => {
                            self.config_service.remove_configuration(&key).await;
                        }
                    }
                }
                ProviderMessage::FirstInit(configs) => {
                    debug!("First init received for configs: {:?}", configs.keys());
                    let config_vec = configs.into_values().collect();
                    self.config_service.update_configurations(config_vec).await;
                }
                ProviderMessage::Error(err) => {
                    error!("Provider error: {}", err);
                }
                ProviderMessage::Shutdown => break,
            }
        }
    }

    pub fn register_provider(&mut self, mut provider: Box<dyn Provider>) {
        debug!("Registering provider: {}", provider.get_name());
        let sender = self.provider_sender.clone();
        tokio::spawn(async move {
            provider.run().await;
            {
                debug!("Provider finished: {}", provider.get_name());
                sender
                    .send(ProviderMessage::Error(
                        "Unexpected end for provider".to_string(),
                    ))
                    .await
                    .unwrap();
            };
        });
    }
}