domo/domo_proto/src/commands/node_management.rs

135 lines
4.4 KiB
Rust

use crate::packet::identifier::Identifier;
use crate::packet::{Packet, ToPacket};
use crate::packet::packet_data::PacketData;
pub enum NodeManagement {
Ping,
RegisterNode { device_id: Identifier },
RemoveNode,
RegisterProperty {
property_name: String,
data_type: u8,
read_only: bool,
},
RemoveProperty {
property_name: String,
},
Error {
error_code: u8,
metadata: [u8; 0xFFFF],
},
}
impl NodeManagement {
fn get_command(&self) -> u8 {
match self {
NodeManagement::Ping => 0x00,
NodeManagement::RegisterNode { .. } => 0x01,
NodeManagement::RemoveNode => 0x02,
NodeManagement::RegisterProperty { .. } => 0x03,
NodeManagement::RemoveProperty { .. } => 0x04,
NodeManagement::Error { .. } => 0x0E
}
}
}
impl Into<NodeManagement> for Packet {
fn into(self) -> NodeManagement {
match self {
Packet::V1 {
src,
dest,
packet_id,
reply_to,
command,
data,
} => match command {
0x00 => NodeManagement::Ping,
0x01 => NodeManagement::RegisterNode { device_id: src },
0x02 => NodeManagement::RemoveNode,
0x03 => NodeManagement::RegisterProperty {
property_name: String::from_utf8(data.get_data()[..32].to_vec()).unwrap(),
data_type: data.get_data()[33],
read_only: data.get_data()[34] != 0
},
0x04 => NodeManagement::RemoveProperty {
property_name: String::from_utf8(data.get_data()[..32].to_vec()).unwrap()
},
0x0E => NodeManagement::Error {
error_code: data.get_data()[0],
metadata: {
let mut metadata = [0_u8; 0xFFFF];
let data_slice = data.get_data();
let metadata_length = u16::from_be_bytes([data_slice[1], data_slice[2]]) as usize;
if metadata_length <= 0xFFFF {
metadata[..metadata_length].copy_from_slice(&data_slice[3..(3 + metadata_length)]);
}
metadata
}
},
_ => unreachable!("Invalid command in Packet::V1"),
},
}
}
}
impl Into<PacketData> for NodeManagement {
fn into(self) -> PacketData {
match self {
NodeManagement::Ping => PacketData::default(),
NodeManagement::RegisterNode { device_id } => PacketData::new(Vec::from(device_id.bytes)),
NodeManagement::RemoveNode => PacketData::default(),
NodeManagement::RegisterProperty { property_name, data_type, read_only } => PacketData::new({
let mut vec = vec![];
vec.extend(property_name.into_bytes());
vec.push(data_type);
vec.push(read_only as u8);
vec
}),
NodeManagement::RemoveProperty { property_name } => PacketData::new(property_name.into_bytes()),
NodeManagement::Error { error_code, metadata } => PacketData::new({
let mut vec = vec![];
vec.push(error_code);
vec.extend_from_slice(metadata.as_ref());
vec
})
}
}
}
impl ToPacket for NodeManagement {
fn to_v1_packet(self, src: Identifier, dest: Identifier, packet_id: Identifier, reply_to: Identifier) -> Packet {
Packet::V1 {
src,
dest,
packet_id,
reply_to,
command: self.get_command(),
data: self.into()
}
}
}
#[allow(non_camel_case_types)]
pub enum NodeManagementError {
net_duplicate_packet,
net_broken_packet,
net_invalid_packet,
errc_not_registered,
errs_not_delivered,
}
impl NodeManagementError {
pub fn error_code(&self) -> u8 {
match self {
NodeManagementError::net_duplicate_packet => 0x00,
NodeManagementError::net_broken_packet => 0x01,
NodeManagementError::net_invalid_packet => 0x02,
NodeManagementError::errc_not_registered => 0x10,
NodeManagementError::errs_not_delivered => 0x20
}
}
}