SolarEnergy/central_backend/src/energy/energy_actor.rs

153 lines
4.2 KiB
Rust
Raw Normal View History

2024-06-29 09:45:39 +00:00
use crate::constants;
use crate::devices::device::{Device, DeviceId, DeviceInfo};
2024-07-01 19:10:45 +00:00
use crate::devices::devices_list::DevicesList;
2024-06-29 09:45:39 +00:00
use crate::energy::consumption;
use crate::energy::consumption::EnergyConsumption;
use actix::prelude::*;
2024-07-02 20:55:51 +00:00
use openssl::x509::X509Req;
2024-06-29 09:45:39 +00:00
pub struct EnergyActor {
curr_consumption: EnergyConsumption,
2024-07-01 19:10:45 +00:00
devices: DevicesList,
2024-06-29 09:45:39 +00:00
}
impl EnergyActor {
pub async fn new() -> anyhow::Result<Self> {
Ok(Self {
curr_consumption: consumption::get_curr_consumption().await?,
2024-07-01 19:10:45 +00:00
devices: DevicesList::load()?,
2024-06-29 09:45:39 +00:00
})
}
async fn refresh(&mut self) -> anyhow::Result<()> {
// Refresh energy
self.curr_consumption = consumption::get_curr_consumption()
.await
.unwrap_or_else(|e| {
log::error!(
"Failed to fetch latest consumption value, will use fallback value! {e}"
);
constants::FALLBACK_PRODUCTION_VALUE
});
Ok(())
}
}
impl Actor for EnergyActor {
type Context = Context<Self>;
fn started(&mut self, ctx: &mut Self::Context) {
log::info!("Energy actor successfully started!");
ctx.run_interval(constants::ENERGY_REFRESH_INTERVAL, |act, _ctx| {
log::info!("Performing energy refresh operation");
if let Err(e) = futures::executor::block_on(act.refresh()) {
log::error!("Energy refresh failed! {e}")
}
});
}
fn stopped(&mut self, _ctx: &mut Self::Context) {
log::info!("Energy actor successfully stopped!");
}
}
pub type EnergyActorAddr = Addr<EnergyActor>;
/// Get current consumption
#[derive(Message)]
#[rtype(result = "EnergyConsumption")]
pub struct GetCurrConsumption;
impl Handler<GetCurrConsumption> for EnergyActor {
type Result = EnergyConsumption;
fn handle(&mut self, _msg: GetCurrConsumption, _ctx: &mut Context<Self>) -> Self::Result {
self.curr_consumption
}
}
2024-07-01 19:10:45 +00:00
/// Get current consumption
#[derive(Message)]
#[rtype(result = "bool")]
2024-07-01 20:24:03 +00:00
pub struct CheckDeviceExists(pub DeviceId);
2024-07-01 19:10:45 +00:00
impl Handler<CheckDeviceExists> for EnergyActor {
type Result = bool;
fn handle(&mut self, msg: CheckDeviceExists, _ctx: &mut Context<Self>) -> Self::Result {
self.devices.exists(&msg.0)
}
}
2024-07-02 20:55:51 +00:00
/// Enroll device
#[derive(Message)]
#[rtype(result = "anyhow::Result<()>")]
pub struct EnrollDevice(pub DeviceId, pub DeviceInfo, pub X509Req);
impl Handler<EnrollDevice> for EnergyActor {
type Result = anyhow::Result<()>;
fn handle(&mut self, msg: EnrollDevice, _ctx: &mut Context<Self>) -> Self::Result {
self.devices.enroll(&msg.0, &msg.1, &msg.2)
}
}
2024-07-03 19:32:32 +00:00
/// Validate a device
#[derive(Message)]
#[rtype(result = "anyhow::Result<()>")]
pub struct ValidateDevice(pub DeviceId);
impl Handler<ValidateDevice> for EnergyActor {
type Result = anyhow::Result<()>;
fn handle(&mut self, msg: ValidateDevice, _ctx: &mut Context<Self>) -> Self::Result {
log::info!("Requested to validate device {:?}...", &msg.0);
self.devices.validate(&msg.0)?;
Ok(())
}
}
2024-07-03 19:10:15 +00:00
/// Delete a device
#[derive(Message)]
#[rtype(result = "anyhow::Result<()>")]
pub struct DeleteDevice(pub DeviceId);
impl Handler<DeleteDevice> for EnergyActor {
type Result = anyhow::Result<()>;
fn handle(&mut self, msg: DeleteDevice, _ctx: &mut Context<Self>) -> Self::Result {
log::info!("Requested to delete device {:?}...", &msg.0);
self.devices.delete(&msg.0)?;
// TODO : delete energy related information
Ok(())
}
}
/// Get the list of devices
#[derive(Message)]
#[rtype(result = "Vec<Device>")]
pub struct GetDeviceLists;
impl Handler<GetDeviceLists> for EnergyActor {
type Result = Vec<Device>;
fn handle(&mut self, _msg: GetDeviceLists, _ctx: &mut Context<Self>) -> Self::Result {
self.devices.full_list()
}
}
/// Get the information about a single device
#[derive(Message)]
#[rtype(result = "Option<Device>")]
pub struct GetSingleDevice(pub DeviceId);
impl Handler<GetSingleDevice> for EnergyActor {
type Result = Option<Device>;
fn handle(&mut self, msg: GetSingleDevice, _ctx: &mut Context<Self>) -> Self::Result {
self.devices.get_single(&msg.0)
}
}