Refactor energy management
This commit is contained in:
@ -5,33 +5,15 @@ use crate::devices::device::{
|
||||
use crate::devices::devices_list::DevicesList;
|
||||
use crate::energy::consumption;
|
||||
use crate::energy::consumption::EnergyConsumption;
|
||||
use crate::energy::engine::EnergyEngine;
|
||||
use crate::utils::time_utils::time_secs;
|
||||
use actix::prelude::*;
|
||||
use openssl::x509::X509Req;
|
||||
use std::collections::HashMap;
|
||||
|
||||
#[derive(Default)]
|
||||
struct DeviceState {
|
||||
last_ping: u64,
|
||||
}
|
||||
|
||||
impl DeviceState {
|
||||
fn is_online(&self) -> bool {
|
||||
(time_secs() - self.last_ping) < constants::DEVICE_MAX_PING_TIME
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Default)]
|
||||
struct RelayState {
|
||||
enabled: bool,
|
||||
since: usize,
|
||||
}
|
||||
|
||||
pub struct EnergyActor {
|
||||
curr_consumption: EnergyConsumption,
|
||||
devices: DevicesList,
|
||||
devices_state: HashMap<DeviceId, DeviceState>,
|
||||
relays_state: HashMap<DeviceRelayID, RelayState>,
|
||||
engine: EnergyEngine,
|
||||
}
|
||||
|
||||
impl EnergyActor {
|
||||
@ -39,20 +21,10 @@ impl EnergyActor {
|
||||
Ok(Self {
|
||||
curr_consumption: consumption::get_curr_consumption().await?,
|
||||
devices: DevicesList::load()?,
|
||||
devices_state: Default::default(),
|
||||
relays_state: Default::default(),
|
||||
engine: EnergyEngine::default(),
|
||||
})
|
||||
}
|
||||
|
||||
fn device_state(&mut self, dev_id: &DeviceId) -> &mut DeviceState {
|
||||
if !self.devices_state.contains_key(dev_id) {
|
||||
self.devices_state
|
||||
.insert(dev_id.clone(), Default::default());
|
||||
}
|
||||
|
||||
self.devices_state.get_mut(dev_id).unwrap()
|
||||
}
|
||||
|
||||
async fn refresh(&mut self) -> anyhow::Result<()> {
|
||||
// Refresh energy
|
||||
self.curr_consumption = consumption::get_curr_consumption()
|
||||
@ -64,6 +36,9 @@ impl EnergyActor {
|
||||
constants::FALLBACK_PRODUCTION_VALUE
|
||||
});
|
||||
|
||||
self.engine
|
||||
.refresh(self.curr_consumption, &self.devices.full_list());
|
||||
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
@ -285,8 +260,7 @@ impl Handler<SynchronizeDevice> for EnergyActor {
|
||||
type Result = anyhow::Result<Vec<RelaySyncStatus>>;
|
||||
|
||||
fn handle(&mut self, msg: SynchronizeDevice, _ctx: &mut Context<Self>) -> Self::Result {
|
||||
let s = self.device_state(&msg.0);
|
||||
s.last_ping = time_secs();
|
||||
self.engine.device_state(&msg.0).record_ping();
|
||||
|
||||
// TODO : implement real code
|
||||
let mut v = vec![];
|
||||
@ -319,7 +293,7 @@ impl Handler<GetDevicesState> for EnergyActor {
|
||||
.full_list()
|
||||
.into_iter()
|
||||
.map(|d| {
|
||||
let s = self.device_state(&d.id);
|
||||
let s = self.engine.device_state(&d.id);
|
||||
ResDevState {
|
||||
id: d.id,
|
||||
last_ping: time_secs() - s.last_ping,
|
||||
|
83
central_backend/src/energy/engine.rs
Normal file
83
central_backend/src/energy/engine.rs
Normal file
@ -0,0 +1,83 @@
|
||||
use crate::constants;
|
||||
use crate::devices::device::{Device, DeviceId, DeviceRelayID};
|
||||
use crate::energy::consumption::EnergyConsumption;
|
||||
use crate::utils::time_utils::time_secs;
|
||||
use prettytable::{row, Table};
|
||||
use std::collections::HashMap;
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct DeviceState {
|
||||
pub last_ping: u64,
|
||||
}
|
||||
|
||||
impl DeviceState {
|
||||
pub fn record_ping(&mut self) {
|
||||
self.last_ping = time_secs();
|
||||
}
|
||||
|
||||
pub fn is_online(&self) -> bool {
|
||||
(time_secs() - self.last_ping) < constants::DEVICE_MAX_PING_TIME
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Default, Clone)]
|
||||
struct RelayState {
|
||||
on: bool,
|
||||
since: usize,
|
||||
}
|
||||
|
||||
#[derive(Default)]
|
||||
pub struct EnergyEngine {
|
||||
devices_state: HashMap<DeviceId, DeviceState>,
|
||||
relays_state: HashMap<DeviceRelayID, RelayState>,
|
||||
}
|
||||
|
||||
impl EnergyEngine {
|
||||
pub fn device_state(&mut self, dev_id: &DeviceId) -> &mut DeviceState {
|
||||
if !self.devices_state.contains_key(dev_id) {
|
||||
self.devices_state
|
||||
.insert(dev_id.clone(), Default::default());
|
||||
}
|
||||
|
||||
self.devices_state.get_mut(dev_id).unwrap()
|
||||
}
|
||||
|
||||
pub fn relay_state(&mut self, relay_id: DeviceRelayID) -> &mut RelayState {
|
||||
if !self.relays_state.contains_key(&relay_id) {
|
||||
self.relays_state.insert(relay_id, Default::default());
|
||||
}
|
||||
|
||||
self.relays_state.get_mut(&relay_id).unwrap()
|
||||
}
|
||||
|
||||
fn print_summary(&mut self, curr_consumption: EnergyConsumption, devices: &[Device]) {
|
||||
log::info!("Current consumption: {curr_consumption}");
|
||||
|
||||
let mut table = Table::new();
|
||||
table.add_row(row!["Device", "Relay", "On", "Since"]);
|
||||
for d in devices {
|
||||
for r in &d.relays {
|
||||
let status = self.relay_state(r.id);
|
||||
table.add_row(row![d.name, r.name, status.on.to_string(), status.since]);
|
||||
}
|
||||
}
|
||||
table.printstd();
|
||||
}
|
||||
|
||||
pub fn refresh(&mut self, curr_consumption: EnergyConsumption, devices: &[Device]) {
|
||||
let new_relays_state = self.relays_state.clone();
|
||||
|
||||
// Forcefully turn off relays that belongs to offline devices
|
||||
|
||||
// Forcefully turn off relays with dependency conflicts
|
||||
|
||||
// Virtually turn off all relays that can be stopped
|
||||
|
||||
// Turn on relays based on priority / dependencies
|
||||
|
||||
// Turn on relays with running constraints
|
||||
|
||||
// Commit changes
|
||||
self.print_summary(curr_consumption, devices); // TODO :replace
|
||||
}
|
||||
}
|
@ -1,2 +1,3 @@
|
||||
pub mod consumption;
|
||||
pub mod energy_actor;
|
||||
pub mod engine;
|
||||
|
Reference in New Issue
Block a user