Xiaomi Vacuum Custom Reminders Part 2
In my last post we saw how to set up HA to track and remind us when to empty our vacuum's dust bin and clean the brush head. Now we want to add automation to remind us that it's time to run a cleanup.
Part 2 - Cleanup Reminders
Back-end Setup
First we need a way to track how long it has been since the last full cleaning, then we need automations when that amount of time reaches certain thresholds. The vacuum exposes a date attribute for when the last cleanup was run, but it gets reset on every cleanup. We only want to track full house cleanups.
In Part 1 we created an automation that triggers after a full house cleanup, so we will leverage that automation to set our new variable. First let's create the variable by adding some code to configuration.yaml
:
input_datetime:
isuck_last_clean_time:
name: iSuck Last Full Clean
has_date: true
has_time: true
Restart HA to create the variable.
Now modify automation.yaml
and add a new action so set the variable. Here is the modified automation from Part 1:
- alias: iSuck Large Clean Complete
trigger:
platform: state
entity_id: vacuum.isuck
from: cleaning
to: returning
condition:
- condition: template
value_template: '{{ state_attr(''vacuum.isuck'', ''cleaned_area'') > 70 }}'
action:
- service: input_datetime.set_datetime
entity_id: input_datetime.isuck_last_clean_time
data_template:
time: '{{ (as_timestamp(state_attr("vacuum.isuck", "clean_start")) | timestamp_custom("%H:%M:%S", true)) }}'
date: '{{ (as_timestamp(state_attr("vacuum.isuck", "clean_start")) | timestamp_custom("%Y-%m-%d", true)) }}'
- service: input_boolean.turn_on
data:
entity_id: input_boolean.isuck_brush_dirty
The automation will set the custom date variable when the cleanup is complete. Note that we are using the clean_start
attribute because we are using our variable to remind when the next cleanup should be started. The clean_start
variable is reset when the cleanup starts, but if you have trouble reading this value you could use the now()
function and subtract the cleaning_time
.
Now we know when the last cleanup was started, but we need a way to track how long it has been since then. The best way to do this is with a template sensor. If you have not set up a sensor before, add the following to your configuration.yaml
:
sensor: !include sensors.yaml
Then add a new file in the config folder called sensors.yaml
along with the following code:
# Enable clock sensors
- platform: time_date
display_options:
- 'time'
- 'date'
- 'date_time'
- 'date_time_iso'
- 'time_date'
- 'time_utc'
- 'beat'
- platform: template
sensors:
vacuum_cleaning_due:
friendly_name: Vacuum Cleaning Due
value_template: >
{% if (states("vacuum.isuck") != 'docked') %}
not_due
{% else %}
{% set now = as_timestamp(states("sensor.date_time_iso")) | float %}
{% set then = as_timestamp(states("input_datetime.isuck_last_clean_time")) | float %}
{% set hours_since_last_clean = ((now - then) / 3600) | round(0) %}
{% if (hours_since_last_clean < 48) %}
not_due
{% elif (hours_since_last_clean < 96) %}
due
{% else %}
overdue
{% endif %}
{% endif %}
One important detail here is that we are enabling and using the built-in the time_date
sensor rather than the now()
function, because the sensor approach will ensure that our new template sensor updates its value in real time. Also note that when the vacuum is not docked, we will assign the value "not_due" so that our UI and Automations don't trigger during a cleanup.
The backend setup is now complete and now you can build UI and automations around the new sensors.
Push Notifications
Now we can build some push notifications using our new sensor to remind us when to vacuum the house. Just like in Part 1 we will add shortcut actions and automatic dismissal.
First we will add an automation to publish the push notifications. The most obvious approach would be a state trigger that pushes a notification when the sensor changes from "not_due" to "due", but that might lead to notifications arriving at inconvenient times during the day. In order to make the notifications more useful, we'll use a time trigger so that we have control over when the notifications will arrive.
Add to automations.yaml
:
- alias: Chore Reminder - Vacuum Cleaning Due Notification
trigger:
- platform: time
at: '08:00:00'
- platform: time
at: '16:00:00'
condition:
- condition: template
value_template: '{{ states("sensor.vacuum_cleaning_due") != "not_due"}}'
- condition: state
entity_id: person.andrew
state: home
action:
- service: notify.html5_notifications
data:
title: iSuck Cleaning Due Today
message: The house is due for a cleaning today.
data:
url: /lovelace/vacuum
actions:
- action: start_isuck_cleaning
title: Start Cleaning
tag: isuck-cleaning-due
The notifications will publish out at 8AM and 4PM if the cleaning is due. There is also a condition to make sure I am home because the notification does me no good if I'm not home to make sure the floors are clear.
Now we just need two more automations. First, we need to listen for the event that's generated when the notification action is tapped, and second, we need to dismiss the notification when a cleaning is started some other way.
automations.yaml
again:
- alias: Vacuum Cleaning Due Notification Complete Event - Start Cleaning
trigger:
- event_data:
action: start_isuck_cleaning
event_type: html5_notification.clicked
platform: event
condition:
- condition: state
entity_id: vacuum.isuck
state: 'docked'
action:
- data:
entity_id: vacuum.isuck
service: vacuum.start
- alias: Vacuum Cleaning Starts - Dismiss Notifications
trigger:
- entity_id: vacuum.isuck
platform: state
to: cleaning
action:
- data:
data:
tag: isuck-cleaning-due
service: notify.html5_dismiss
Note that we added one condition to make sure the vacuum is docked before starting a new cleanup. If the vacuum is undocked, it's either cleaning, stuck for some reason.
Now all of the automations are in place to remind us when to vacuum the house!