This commit is contained in:
parent
db17b68e90
commit
5333d8042f
|
@ -87,16 +87,18 @@ impl GoogleHome {
|
||||||
.into_iter()
|
.into_iter()
|
||||||
.map(|device| device.id)
|
.map(|device| device.id)
|
||||||
.map(|id| async move {
|
.map(|id| async move {
|
||||||
// NOTE: Requires let_chains feature
|
// NOTE: Requires let_chains feature
|
||||||
let device = if let Some(device) = devices.get(id.as_str()) && let Some(device) = device.read().await.as_ref().cast() {
|
let device = if let Some(device) = devices.get(id.as_str())
|
||||||
device.query().await
|
&& let Some(device) = device.read().await.as_ref().cast()
|
||||||
} else {
|
{
|
||||||
let mut device = query::Device::new();
|
device.query().await
|
||||||
device.set_offline();
|
} else {
|
||||||
device.set_error(DeviceError::DeviceNotFound.into());
|
let mut device = query::Device::new();
|
||||||
|
device.set_offline();
|
||||||
|
device.set_error(DeviceError::DeviceNotFound.into());
|
||||||
|
|
||||||
device
|
device
|
||||||
};
|
};
|
||||||
|
|
||||||
(id, device)
|
(id, device)
|
||||||
});
|
});
|
||||||
|
@ -114,83 +116,84 @@ impl GoogleHome {
|
||||||
let resp_payload = Arc::new(Mutex::new(response::execute::Payload::new()));
|
let resp_payload = Arc::new(Mutex::new(response::execute::Payload::new()));
|
||||||
|
|
||||||
let f = payload.commands.into_iter().map(|command| {
|
let f = payload.commands.into_iter().map(|command| {
|
||||||
let resp_payload = resp_payload.clone();
|
let resp_payload = resp_payload.clone();
|
||||||
async move {
|
async move {
|
||||||
let mut success = response::execute::Command::new(execute::Status::Success);
|
let mut success = response::execute::Command::new(execute::Status::Success);
|
||||||
success.states = Some(execute::States {
|
success.states = Some(execute::States {
|
||||||
online: true,
|
online: true,
|
||||||
state: State::default(),
|
state: State::default(),
|
||||||
});
|
});
|
||||||
let mut offline = response::execute::Command::new(execute::Status::Offline);
|
let mut offline = response::execute::Command::new(execute::Status::Offline);
|
||||||
offline.states = Some(execute::States {
|
offline.states = Some(execute::States {
|
||||||
online: false,
|
online: false,
|
||||||
state: State::default(),
|
state: State::default(),
|
||||||
});
|
});
|
||||||
let mut errors: HashMap<ErrorCode, response::execute::Command> = HashMap::new();
|
let mut errors: HashMap<ErrorCode, response::execute::Command> = HashMap::new();
|
||||||
|
|
||||||
let f = command
|
let f = command
|
||||||
.devices
|
.devices
|
||||||
.into_iter()
|
.into_iter()
|
||||||
.map(|device| device.id)
|
.map(|device| device.id)
|
||||||
.map(|id| {
|
.map(|id| {
|
||||||
let execution = command.execution.clone();
|
let execution = command.execution.clone();
|
||||||
async move {
|
async move {
|
||||||
if let Some(device) = devices.get(id.as_str()) && let Some(device) = device.write().await.as_mut().cast_mut() {
|
if let Some(device) = devices.get(id.as_str())
|
||||||
if !device.is_online() {
|
&& let Some(device) = device.write().await.as_mut().cast_mut()
|
||||||
return (id, Ok(false));
|
{
|
||||||
}
|
if !device.is_online() {
|
||||||
|
return (id, Ok(false));
|
||||||
|
}
|
||||||
|
|
||||||
// NOTE: We can not use .map here because async =(
|
// NOTE: We can not use .map here because async =(
|
||||||
let mut results = Vec::new();
|
let mut results = Vec::new();
|
||||||
for cmd in &execution {
|
for cmd in &execution {
|
||||||
results.push(device.execute(cmd).await);
|
results.push(device.execute(cmd).await);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Convert vec of results to a result with a vec and the first
|
// Convert vec of results to a result with a vec and the first
|
||||||
// encountered error
|
// encountered error
|
||||||
let results = results
|
let results =
|
||||||
.into_iter()
|
results.into_iter().collect::<Result<Vec<_>, ErrorCode>>();
|
||||||
.collect::<Result<Vec<_>, ErrorCode>>();
|
|
||||||
|
|
||||||
// TODO: We only get one error not all errors
|
// TODO: We only get one error not all errors
|
||||||
if let Err(err) = results {
|
if let Err(err) = results {
|
||||||
(id, Err(err))
|
(id, Err(err))
|
||||||
} else {
|
} else {
|
||||||
(id, Ok(true))
|
(id, Ok(true))
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
(id.clone(), Err(DeviceError::DeviceNotFound.into()))
|
(id.clone(), Err(DeviceError::DeviceNotFound.into()))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
let a = join_all(f).await;
|
let a = join_all(f).await;
|
||||||
a.into_iter().for_each(|(id, state)| {
|
a.into_iter().for_each(|(id, state)| {
|
||||||
match state {
|
match state {
|
||||||
Ok(true) => success.add_id(&id),
|
Ok(true) => success.add_id(&id),
|
||||||
Ok(false) => offline.add_id(&id),
|
Ok(false) => offline.add_id(&id),
|
||||||
Err(err) => errors
|
Err(err) => errors
|
||||||
.entry(err)
|
.entry(err)
|
||||||
.or_insert_with(|| match &err {
|
.or_insert_with(|| match &err {
|
||||||
ErrorCode::DeviceError(_) => {
|
ErrorCode::DeviceError(_) => {
|
||||||
response::execute::Command::new(execute::Status::Error)
|
response::execute::Command::new(execute::Status::Error)
|
||||||
}
|
}
|
||||||
ErrorCode::DeviceException(_) => {
|
ErrorCode::DeviceException(_) => {
|
||||||
response::execute::Command::new(execute::Status::Exceptions)
|
response::execute::Command::new(execute::Status::Exceptions)
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
.add_id(&id),
|
.add_id(&id),
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
|
|
||||||
let mut resp_payload = resp_payload.lock().await;
|
let mut resp_payload = resp_payload.lock().await;
|
||||||
resp_payload.add_command(success);
|
resp_payload.add_command(success);
|
||||||
resp_payload.add_command(offline);
|
resp_payload.add_command(offline);
|
||||||
for (error, mut cmd) in errors {
|
for (error, mut cmd) in errors {
|
||||||
cmd.error_code = Some(error);
|
cmd.error_code = Some(error);
|
||||||
resp_payload.add_command(cmd);
|
resp_payload.add_command(cmd);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
join_all(f).await;
|
join_all(f).await;
|
||||||
|
|
|
@ -181,7 +181,9 @@ impl OnMqtt for ContactSensor {
|
||||||
let mut light = light.write().await;
|
let mut light = light.write().await;
|
||||||
if !previous {
|
if !previous {
|
||||||
// If the timeout is zero just turn the light off directly
|
// If the timeout is zero just turn the light off directly
|
||||||
if trigger.timeout.is_zero() && let Some(light) = As::<dyn OnOff>::cast_mut(light.as_mut()) {
|
if trigger.timeout.is_zero()
|
||||||
|
&& let Some(light) = As::<dyn OnOff>::cast_mut(light.as_mut())
|
||||||
|
{
|
||||||
light.set_on(false).await.ok();
|
light.set_on(false).await.ok();
|
||||||
} else if let Some(light) = As::<dyn Timeout>::cast_mut(light.as_mut()) {
|
} else if let Some(light) = As::<dyn Timeout>::cast_mut(light.as_mut()) {
|
||||||
light.start_timeout(trigger.timeout).await.unwrap();
|
light.start_timeout(trigger.timeout).await.unwrap();
|
||||||
|
|
|
@ -157,8 +157,8 @@ impl OnMqtt for IkeaOutlet {
|
||||||
|
|
||||||
// If this is a kettle start a timeout for turning it of again
|
// If this is a kettle start a timeout for turning it of again
|
||||||
if state && let Some(timeout) = self.timeout {
|
if state && let Some(timeout) = self.timeout {
|
||||||
self.start_timeout(timeout).await.unwrap();
|
self.start_timeout(timeout).await.unwrap();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
let action = match RemoteMessage::try_from(message) {
|
let action = match RemoteMessage::try_from(message) {
|
||||||
Ok(message) => message.action(),
|
Ok(message) => message.action(),
|
||||||
|
|
Loading…
Reference in New Issue
Block a user