use serde::{Deserialize, Serialize};
use std::io::{Read, Write};
use kasimir_sys;
#[derive(Serialize, Deserialize, Debug)]
struct GenericEmptyRequest {}
#[derive(Serialize, Deserialize, Debug)]
struct SetRelayStateRequest {
state: i32,
}
#[derive(Serialize, Deserialize, Debug)]
struct SetLedOffRequest {
off: i32,
}
#[derive(Serialize, Deserialize, Debug)]
struct SetDevAliasRequest {
alias: String,
}
#[derive(Serialize, Deserialize, Debug)]
struct SystemRequest {
#[serde(skip_serializing_if="Option::is_none")]
get_sysinfo: Option<GenericEmptyRequest>,
#[serde(skip_serializing_if="Option::is_none")]
set_relay_state: Option<SetRelayStateRequest>,
#[serde(skip_serializing_if="Option::is_none")]
set_led_off: Option<SetLedOffRequest>,
#[serde(skip_serializing_if="Option::is_none")]
set_dev_alias: Option<SetDevAliasRequest>,
}
#[derive(Serialize, Deserialize, Debug)]
struct AddScheduleRuleRequest {
day: i32, eact: i32,
emin: i32, enable: i32,
etime_opt: i32, month: i32, name: String,
repeat: i32,
sact: i32,
smin: i32,
stime_opt: i32,
wday: [i32; 7],
year: i32, }
#[derive(Serialize, Deserialize, Debug)]
struct EditScheduleRuleRequest {
id: String,
#[serde(flatten)]
add_rule_request: AddScheduleRuleRequest,
}
#[derive(Serialize, Deserialize, Debug)]
struct SetOverallEnableRequest {
enable: i32,
}
#[derive(Serialize, Deserialize, Debug)]
struct ScheduleRequest {
#[serde(skip_serializing_if="Option::is_none")]
add_rule: Option<AddScheduleRuleRequest>,
#[serde(skip_serializing_if="Option::is_none")]
edit_rule: Option<EditScheduleRuleRequest>,
#[serde(skip_serializing_if="Option::is_none")]
set_overall_enable: Option<SetOverallEnableRequest>,
#[serde(skip_serializing_if="Option::is_none")]
get_rules: Option<GenericEmptyRequest>,
#[serde(skip_serializing_if="Option::is_none")]
delete_all_rules: Option<GenericEmptyRequest>,
}
#[derive(Serialize, Deserialize, Debug)]
struct AddAntiTheftRuleRequest {
day: i32,
duration: i32,
emin: i32,
enable: i32,
etime_opt: i32,
force: i32,
frequency: i32,
lastFor: i32,
latitude: f32,
longitude: f32,
month: i32,
name: String,
repeat: i32,
smin: i32,
stime_opt: i32,
wday: [i32; 7],
year: i32,
}
#[derive(Serialize, Deserialize, Debug)]
struct EditAntiTheftRuleRequest {
id: String,
#[serde(flatten)]
add_rule_request: AddAntiTheftRuleRequest,
}
#[derive(Serialize, Deserialize, Debug)]
struct AntiTheftRequest {
#[serde(skip_serializing_if="Option::is_none")]
add_rule: Option<AddAntiTheftRuleRequest>,
#[serde(skip_serializing_if="Option::is_none")]
edit_rule: Option<EditAntiTheftRuleRequest>,
#[serde(skip_serializing_if="Option::is_none")]
set_overall_enable: Option<SetOverallEnableRequest>,
#[serde(skip_serializing_if="Option::is_none")]
get_rules: Option<GenericEmptyRequest>,
#[serde(skip_serializing_if="Option::is_none")]
delete_all_rules: Option<GenericEmptyRequest>,
}
#[derive(Serialize, Deserialize, Debug)]
struct AddCountDownRuleRequest {
act: i32,
delay: i32,
enable: i32,
name: String,
}
#[derive(Serialize, Deserialize, Debug)]
struct EditCountDownRuleRequest {
id: String,
#[serde(flatten)]
add_rule_request: AddCountDownRuleRequest,
}
#[derive(Serialize, Deserialize, Debug)]
struct CountDownRequest {
#[serde(skip_serializing_if="Option::is_none")]
add_rule: Option<AddCountDownRuleRequest>,
#[serde(skip_serializing_if="Option::is_none")]
edit_rule: Option<EditCountDownRuleRequest>,
#[serde(skip_serializing_if="Option::is_none")]
set_overall_enable: Option<SetOverallEnableRequest>,
#[serde(skip_serializing_if="Option::is_none")]
get_rules: Option<GenericEmptyRequest>,
#[serde(skip_serializing_if="Option::is_none")]
delete_all_rules: Option<GenericEmptyRequest>,
}
#[derive(Serialize, Deserialize, Debug)]
struct SetStainfoRequest {
key_type: i32,
password: String,
ssid: String,
}
#[derive(Serialize, Deserialize, Debug)]
struct NetifRequest {
#[serde(skip_serializing_if="Option::is_none")]
set_stainfo: Option<SetStainfoRequest>,
#[serde(skip_serializing_if="Option::is_none")]
get_stainfo: Option<GenericEmptyRequest>,
}
#[derive(Serialize, Deserialize, Debug)]
struct OptionRequest {
#[serde(skip_serializing_if="Option::is_none")]
source: Option<String>,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct Request {
#[serde(skip_serializing_if="Option::is_none")]
system: Option<SystemRequest>,
#[serde(skip_serializing_if="Option::is_none")]
schedule: Option<ScheduleRequest>,
#[serde(skip_serializing_if="Option::is_none")]
anti_theft: Option<AntiTheftRequest>,
#[serde(skip_serializing_if="Option::is_none")]
count_down: Option<CountDownRequest>,
#[serde(skip_serializing_if="Option::is_none")]
netif: Option<NetifRequest>,
#[serde(skip_serializing_if="Option::is_none")]
option: Option<OptionRequest>, }
#[derive(Serialize, Deserialize, Debug)]
struct NextActionResponse {
r#type: Option<i32>,
}
#[derive(Serialize, Deserialize, Debug)]
struct GetSysinfoResponse {
sw_ver: Option<String>,
hw_ver: Option<String>,
model: Option<String>,
deviceId: Option<String>,
oemId: Option<String>,
hwId: Option<String>,
rssi: Option<i32>,
longitude_i: Option<i32>,
latitude_i: Option<i32>,
alias: Option<String>,
status: Option<String>,
mic_type: Option<String>,
feature: Option<String>,
mac: Option<String>,
updating: Option<i32>,
led_off: Option<i32>,
obd_src: Option<String>,
relay_state: Option<i32>,
on_time: Option<i32>,
active_mode: Option<String>,
icon_hash: Option<String>,
dev_name: Option<String>,
next_action: Option<NextActionResponse>,
ntc_state: Option<i32>,
err_code: i32,
err_msg: Option<String>,
}
#[derive(Serialize, Deserialize, Debug)]
struct GenericSetResponse {
err_code: i32,
err_msg: Option<String>,
}
#[derive(Serialize, Deserialize, Debug)]
struct GenericAddResponse {
id: Option<String>,
err_code: i32,
err_msg: Option<String>,
}
#[derive(Serialize, Deserialize, Debug)]
struct SystemResponse {
get_sysinfo: Option<GetSysinfoResponse>,
set_relay_state: Option<GenericSetResponse>,
set_led_off: Option<GenericSetResponse>,
set_dev_alias: Option<GenericSetResponse>,
}
#[derive(Serialize, Deserialize, Debug)]
struct GetScheduleRuleResponse {
id: String,
eact: i32,
enable: i32,
name: String,
repeat: i32,
sact: i32,
smin: i32,
soffset: Option<i32>,
stime_opt: i32,
wday: [i32; 7],
}
#[derive(Serialize, Deserialize, Debug)]
struct GetScheduleRulesResponse {
rule_list: Option<Vec<GetScheduleRuleResponse>>,
enable: Option<i32>,
version: Option<i32>,
err_code: i32,
err_msg: Option<String>,
}
#[derive(Serialize, Deserialize, Debug)]
struct ScheduleResponse {
add_rule: Option<GenericAddResponse>,
edit_rule: Option<GenericSetResponse>,
set_overall_enable: Option<GenericSetResponse>,
get_rules: Option<GetScheduleRulesResponse>,
delete_rule: Option<GenericSetResponse>,
delete_all_rules: Option<GenericSetResponse>,
}
#[derive(Serialize, Deserialize, Debug)]
struct GetAntiTheftRuleResponse {
id: String,
emin: i32,
enable: i32,
etime_opt: i32,
frequency: i32,
name: String,
repeat: i32,
smin: i32,
stime_opt: i32,
wday: [i32; 7],
}
#[derive(Serialize, Deserialize, Debug)]
struct GetAntiTheftRulesResponse {
rule_list: Option<Vec<GetAntiTheftRuleResponse>>,
enable: Option<i32>,
version: Option<i32>,
err_code: i32,
err_msg: Option<String>,
}
#[derive(Serialize, Deserialize, Debug)]
struct AntiTheftResponse {
add_rule: Option<GenericAddResponse>,
edit_rule: Option<GenericSetResponse>,
set_overall_enable: Option<GenericSetResponse>,
get_rules: Option<GetAntiTheftRulesResponse>,
delete_rule: Option<GenericSetResponse>,
delete_all_rules: Option<GenericSetResponse>,
}
#[derive(Serialize, Deserialize, Debug)]
struct GetCountDownRuleResponse {
id: String,
remain: i32,
act: i32,
delay: i32,
enable: i32,
name: String,
}
#[derive(Serialize, Deserialize, Debug)]
struct GetCountDownRulesResponse {
rule_list: Option<Vec<GetCountDownRuleResponse>>,
err_code: i32,
err_msg: Option<String>,
}
#[derive(Serialize, Deserialize, Debug)]
struct CountDownResponse {
add_rule: Option<GenericAddResponse>,
edit_rule: Option<GenericSetResponse>,
set_overall_enable: Option<GenericSetResponse>,
get_rules: Option<GetCountDownRulesResponse>,
delete_rule: Option<GenericSetResponse>,
delete_all_rules: Option<GenericSetResponse>,
}
#[derive(Serialize, Deserialize, Debug)]
struct GetStainfoResponse {
ssid: Option<String>,
key_type: Option<i32>,
rssi: Option<i32>,
err_code: i32,
err_msg: Option<String>,
}
#[derive(Serialize, Deserialize, Debug)]
struct NetifResponse {
set_stainfo: Option<GenericSetResponse>,
get_stainfo: Option<GetStainfoResponse>,
}
#[derive(Serialize, Deserialize, Debug)]
pub struct Response {
system: Option<SystemResponse>,
schedule: Option<ScheduleResponse>,
anti_theft: Option<AntiTheftResponse>,
count_down: Option<CountDownResponse>,
netif: Option<NetifResponse>,
}
#[derive(Debug)]
pub enum ErrorCode {
ModuleNotSupported, MemberNotSupported, InvalidArgument, EntryDoesNotExist, UnknownError(i32, String),
FieldMissing(String),
}
#[derive(Debug)]
pub enum Error {
ConversionError(serde_json::Error),
IoError(std::io::Error),
ErrorResponse(ErrorCode),
}
impl From<serde_json::Error> for Error {
fn from(error: serde_json::Error) -> Self {
Error::ConversionError(error)
}
}
impl From<std::io::Error> for Error {
fn from(error: std::io::Error) -> Self {
Error::IoError(error)
}
}
impl From<ErrorCode> for Error {
fn from(error: ErrorCode) -> Self {
Error::ErrorResponse(error)
}
}
#[derive(Debug)]
pub struct State {
pub relay: bool,
pub led: bool,
pub updating: bool,
}
#[derive(Debug)]
pub struct Settings {
pub alias: String,
pub longitude: i32,
pub latitude: i32,
}
#[derive(Debug)]
pub struct Device {
pub model: String,
pub hardware_version: String,
pub software_version: String,
pub device_id: String,
pub hardware_id: String,
pub oem_id: String,
}
#[derive(Debug)]
pub struct Info {
pub mac_address: String,
pub on_time_sec: i32,
pub active_mode: String, pub next_action: i32, pub wifi_rssi: i32,
}
#[derive(Debug)]
pub struct SysInfo {
pub state: State,
pub settings: Settings,
pub device: Device,
pub info: Info,
}
use std::convert::{TryFrom, TryInto};
fn field_missing(s: &str) -> ErrorCode {
ErrorCode::FieldMissing(s.to_owned())
}
impl TryFrom<GetSysinfoResponse> for SysInfo {
type Error = ErrorCode;
fn try_from(sysinfo: GetSysinfoResponse) -> Result<Self, Self::Error> {
if sysinfo.err_code != 0 {
let error_message = sysinfo.err_msg.unwrap_or("<No error message found>".to_string());
return Err(ErrorCode::UnknownError(sysinfo.err_code, error_message));
}
Ok(SysInfo {
state: State {
relay: 0 != sysinfo.relay_state.ok_or(field_missing("relay_state"))?,
led: 0 == sysinfo.led_off.ok_or(field_missing("led_off"))?,
updating: 0 != sysinfo.updating.ok_or(field_missing("updating"))?,
},
settings: Settings {
alias: sysinfo.alias.ok_or(field_missing("alias"))?,
longitude: sysinfo.longitude_i.ok_or(field_missing("longitude_i"))?,
latitude: sysinfo.latitude_i.ok_or(field_missing("latitude_i"))?,
},
device: Device {
model: sysinfo.model.ok_or(field_missing("model"))?,
hardware_version: sysinfo.hw_ver.ok_or(field_missing("hw_ver"))?,
software_version: sysinfo.sw_ver.ok_or(field_missing("sw_ver"))?,
device_id: sysinfo.deviceId.ok_or(field_missing("deviceId"))?,
hardware_id: sysinfo.hwId.ok_or(field_missing("hwId"))?,
oem_id: sysinfo.oemId.ok_or(field_missing("oemId"))?,
},
info: Info {
mac_address: sysinfo.mac.ok_or(field_missing("mac"))?,
on_time_sec: sysinfo.on_time.ok_or(field_missing("on_time"))?,
active_mode: sysinfo.active_mode.ok_or(field_missing("active_mode"))?,
next_action: sysinfo.next_action.ok_or(field_missing("next_action"))?
.r#type.ok_or(field_missing("next_action.type"))?,
wifi_rssi: sysinfo.rssi.ok_or(field_missing("rssi"))?,
},
})
}
}
#[derive(Debug)]
pub struct ScheduleRule {
pub id: Option<String>,
pub name: String,
pub relay: bool,
pub enabled: bool,
pub weekday: [bool; 7], pub repeating: bool,
pub time_min: i32, pub option: i32,
pub opt_offset: Option<i32>,
}
impl TryFrom<GetScheduleRulesResponse> for Vec<ScheduleRule> {
type Error = ErrorCode;
fn try_from(rules: GetScheduleRulesResponse) -> Result<Self, Self::Error> {
if rules.err_code != 0 {
let error_message = rules.err_msg.unwrap_or("<No error message found>".to_string());
return Err(ErrorCode::UnknownError(rules.err_code, error_message));
}
let rule_list = rules.rule_list.ok_or(field_missing("rule_list"))?;
rule_list.into_iter().map(
|rule| -> Result<ScheduleRule, ErrorCode> {
Ok(ScheduleRule {
id: Some(rule.id),
name: rule.name,
relay: 0 != rule.eact,
enabled: 0 != rule.enable,
weekday: rule.wday.into_iter().map(|x| 0 != *x).collect::<Vec<bool>>().try_into().unwrap(),
repeating: 0 != rule.repeat,
time_min: rule.smin,
option: rule.stime_opt,
opt_offset: rule.soffset,
})
}).collect()
}
}
impl TryFrom<GenericSetResponse> for () {
type Error = ErrorCode;
fn try_from(set_response: GenericSetResponse) -> Result<Self, Self::Error> {
if set_response.err_code != 0 {
let error_message = set_response.err_msg.unwrap_or("<No error message found>".to_string());
return Err(ErrorCode::UnknownError(set_response.err_code, error_message));
}
Ok(())
}
}
impl TryFrom<GenericAddResponse> for String {
type Error = ErrorCode;
fn try_from(add_response: GenericAddResponse) -> Result<Self, Self::Error> {
if add_response.err_code != 0 {
let error_message = add_response.err_msg.unwrap_or("<No error message found>".to_string());
return Err(ErrorCode::UnknownError(add_response.err_code, error_message));
}
Ok(add_response.id.ok_or(field_missing("id"))?)
}
}
#[derive(Debug)]
pub struct AntiTheftRule {
pub id: Option<String>,
pub name: String,
pub enabled: bool,
pub weekday: [bool; 7], pub repeating: bool,
pub start_time_min: i32, pub end_time_min: i32,
pub frequency: i32,
}
impl TryFrom<GetAntiTheftRulesResponse> for Vec<AntiTheftRule> {
type Error = ErrorCode;
fn try_from(rules: GetAntiTheftRulesResponse) -> Result<Self, Self::Error> {
if rules.err_code != 0 {
let error_message = rules.err_msg.unwrap_or("<No error message found>".to_string());
return Err(ErrorCode::UnknownError(rules.err_code, error_message));
}
let rule_list = rules.rule_list.ok_or(field_missing("rule_list"))?;
rule_list.into_iter().map(
|rule| -> Result<AntiTheftRule, ErrorCode> {
Ok(AntiTheftRule {
id: Some(rule.id),
name: rule.name,
enabled: 0 != rule.enable,
weekday: rule.wday.into_iter().map(|x| 0 != *x).collect::<Vec<bool>>().try_into().unwrap(),
repeating: 0 != rule.repeat,
start_time_min: rule.smin,
end_time_min: rule.emin,
frequency: rule.frequency,
})
}).collect()
}
}
#[derive(Debug)]
pub struct CountDownRule {
pub id: Option<String>,
pub name: String,
pub delay_sec: i32,
pub remaining_sec: Option<i32>,
pub relay: bool,
pub enabled: bool,
}
impl TryFrom<GetCountDownRulesResponse> for Vec<CountDownRule> {
type Error = ErrorCode;
fn try_from(rules: GetCountDownRulesResponse) -> Result<Self, Self::Error> {
if rules.err_code != 0 {
let error_message = rules.err_msg.unwrap_or("<No error message found>".to_string());
return Err(ErrorCode::UnknownError(rules.err_code, error_message));
}
let rule_list = rules.rule_list.ok_or(field_missing("rule_list"))?;
rule_list.into_iter().map(
|rule| -> Result<CountDownRule, ErrorCode> {
Ok(CountDownRule {
id: Some(rule.id),
name: rule.name,
relay: 0 != rule.act,
delay_sec: rule.delay,
remaining_sec: Some(rule.remain),
enabled: 0 != rule.enable,
})
}).collect()
}
}
pub fn get_sys_info<T: Read + Write + ?Sized>(stream: &mut T) -> Result<SysInfo, Error> {
let request = Request {
system: Some(SystemRequest {
get_sysinfo: Some(GenericEmptyRequest {}),
set_relay_state: None,
set_led_off: None,
set_dev_alias: None,
}),
schedule: None,
anti_theft: None,
count_down: None,
netif: None,
option: None,
};
let result = run_request(stream, &request)?;
let sysinfo = result.system.unwrap().get_sysinfo.unwrap().try_into()?;
Ok(sysinfo)
}
pub fn get_schedule_rules<T: Read + Write + ?Sized>(stream: &mut T) -> Result<Vec<ScheduleRule>, Error> {
let request = Request {
system: None,
schedule: Some(ScheduleRequest {
add_rule: None,
edit_rule: None,
set_overall_enable: None,
get_rules: Some(GenericEmptyRequest {}),
delete_all_rules: None,
}),
anti_theft: None,
count_down: None,
netif: None,
option: None,
};
let result = run_request(stream, &request)?;
let rules = result.schedule.unwrap().get_rules.unwrap().try_into()?;
Ok(rules)
}
impl From<ScheduleRule> for AddScheduleRuleRequest {
fn from(rule: ScheduleRule) -> Self {
AddScheduleRuleRequest {
day: 0, eact: 0,
emin: 0, enable: if rule.enabled {1} else {0},
etime_opt: 0, month: 0, name: rule.name,
repeat: if rule.repeating {1} else {0},
sact: if rule.relay {1} else {0},
smin: rule.time_min,
stime_opt: 0,
wday: [1,1,1,1,1,1,1],
year: 0, }
}
}
impl From<ScheduleRule> for Option<EditScheduleRuleRequest> {
fn from(rule: ScheduleRule) -> Self {
Some(EditScheduleRuleRequest {
id: rule.id.clone()?,
add_rule_request: rule.into(),
})
}
}
impl From<bool> for SetOverallEnableRequest {
fn from(value: bool) -> Self {
SetOverallEnableRequest {
enable: if value {1} else {0},
}
}
}
pub fn add_schedule_rule<T: Read + Write + ?Sized>(stream: &mut T, rule: ScheduleRule) -> Result<String, Error> {
let request = Request {
system: None,
schedule: Some(ScheduleRequest {
add_rule: Some(rule.into()),
edit_rule: None,
set_overall_enable: None,
get_rules: None,
delete_all_rules: None,
}),
anti_theft: None,
count_down: None,
netif: None,
option: None,
};
let result = run_request(stream, &request)?;
Ok(result.schedule.unwrap().add_rule.unwrap().try_into()?)
}
pub fn edit_schedule_rule<T: Read + Write + ?Sized>(stream: &mut T, rule: ScheduleRule) -> Result<(), Error> {
let request = Request {
system: None,
schedule: Some(ScheduleRequest {
add_rule: None,
edit_rule: rule.into(),
set_overall_enable: None,
get_rules: None,
delete_all_rules: None,
}),
anti_theft: None,
count_down: None,
netif: None,
option: None,
};
let result = run_request(stream, &request)?;
Ok(result.schedule.unwrap().edit_rule.unwrap().try_into()?)
}
pub fn set_overall_enable_schedule<T: Read + Write + ?Sized>(stream: &mut T, enabled: bool) -> Result<(), Error> {
let request = Request {
system: None,
schedule: Some(ScheduleRequest {
add_rule: None,
edit_rule: None,
set_overall_enable: Some(enabled.into()),
get_rules: None,
delete_all_rules: None,
}),
anti_theft: None,
count_down: None,
netif: None,
option: None,
};
let result = run_request(stream, &request)?;
Ok(result.schedule.unwrap().set_overall_enable.unwrap().try_into()?)
}
impl From<AntiTheftRule> for AddAntiTheftRuleRequest {
fn from(rule: AntiTheftRule) -> Self {
AddAntiTheftRuleRequest {
day: 0,
duration: 0, emin: rule.end_time_min,
enable: if rule.enabled {1} else {0},
etime_opt: 0,
force: 0,
frequency: rule.frequency,
lastFor: 0,
latitude: 0.0,
longitude: 0.0,
month: 0,
name: rule.name,
repeat: if rule.repeating {1} else {0},
smin: rule.start_time_min,
stime_opt: 0,
wday: [1,1,1,1,1,1,1],
year: 0,
}
}
}
pub fn add_anti_theft_rule<T: Read + Write + ?Sized>(stream: &mut T, rule: AntiTheftRule) -> Result<(), Error> {
let request = Request {
system: None,
schedule: None,
anti_theft: Some(AntiTheftRequest {
add_rule: Some(rule.into()),
edit_rule: None,
set_overall_enable: None,
get_rules: None,
delete_all_rules: None,
}),
count_down: None,
netif: None,
option: None,
};
let result = run_request(stream, &request)?;
Ok(())
}
impl From<CountDownRule> for AddCountDownRuleRequest {
fn from(rule: CountDownRule) -> Self {
AddCountDownRuleRequest {
act: if rule.relay {1} else {0},
delay: rule.delay_sec,
enable: if rule.enabled {1} else {0},
name: rule.name,
}
}
}
pub fn add_count_down_rule<T: Read + Write + ?Sized>(stream: &mut T, rule: CountDownRule) -> Result<(), Error> {
let request = Request {
system: None,
schedule: None,
anti_theft: None,
count_down: Some(CountDownRequest {
add_rule: Some(rule.into()),
edit_rule: None,
set_overall_enable: None,
get_rules: None,
delete_all_rules: None,
}),
netif: None,
option: None,
};
let result = run_request(stream, &request)?;
Ok(())
}
pub fn get_anti_theft_rules<T: Read + Write + ?Sized>(stream: &mut T) -> Result<Vec<AntiTheftRule>, Error> {
let request = Request {
system: None,
schedule: None,
anti_theft: Some(AntiTheftRequest {
add_rule: None,
edit_rule: None,
set_overall_enable: None,
get_rules: Some(GenericEmptyRequest {}),
delete_all_rules: None,
}),
count_down: None,
netif: None,
option: None,
};
let result = run_request(stream, &request)?;
let rules = result.anti_theft.unwrap().get_rules.unwrap().try_into()?;
Ok(rules)
}
pub fn get_count_down_rules<T: Read + Write + ?Sized>(stream: &mut T) -> Result<Vec<CountDownRule>, Error> {
let request = Request {
system: None,
schedule: None,
anti_theft: None,
count_down: Some(CountDownRequest {
add_rule: None,
edit_rule: None,
set_overall_enable: None,
get_rules: Some(GenericEmptyRequest {}),
delete_all_rules: None,
}),
netif: None,
option: None,
};
let result = run_request(stream, &request)?;
let rules = result.count_down.unwrap().get_rules.unwrap().try_into()?;
Ok(rules)
}
pub fn get_sys_info_str<T: Read + Write + ?Sized>(stream: &mut T) {
let data = Request {
system: Some(SystemRequest {
get_sysinfo: Some(GenericEmptyRequest {}),
set_relay_state: None,
set_led_off: None,
set_dev_alias: None,
}),
schedule: None,
anti_theft: None,
count_down: None,
netif: None,
option: None,
};
let serialized = serde_json::to_string(&data).unwrap();
println!("Rqs: {}", serialized);
kasimir_sys::write_hs100_str(stream, serialized);
let response = &kasimir_sys::read_hs100_str(stream).unwrap();
println!("Rsp: {}", response);
let deserialized: Response =
serde_json::from_str(response).unwrap();
println!("Answer: {:#?}", deserialized);
}
pub fn general_request_str<T: Read + Write + ?Sized>(stream: &mut T, text: &str) {
let serialized = text.to_string();
println!("Rqs: {}", serialized);
kasimir_sys::write_hs100_str(stream, serialized);
let response = &kasimir_sys::read_hs100_str(stream).unwrap();
println!("Rsp: {}", response);
std::io::stdout().flush();
let deserialized: Response =
serde_json::from_str(response).unwrap();
println!("Answer: {:#?}", deserialized);
}
pub fn run_request<T: Read + Write + ?Sized>(stream: &mut T, request: &Request) -> Result<Response, Error> {
let serialized = serde_json::to_string(request)?;
println!("Rqs: {}", serialized);
kasimir_sys::write_hs100_str(stream, serialized);
let response = &kasimir_sys::read_hs100_str(stream)?;
println!("Rsp: {}", response);
Ok(serde_json::from_str(response)?)
}
#[cfg(test)]
mod tests {
#[test]
fn it_works() {
super::get_sys_info();
assert_eq!(2 + 2, 4);
}
}