Skip to content

Instantly share code, notes, and snippets.

@cbenard
Last active June 22, 2025 16:57
Show Gist options
  • Save cbenard/8558b1b82359a70df661c17efe1f99d4 to your computer and use it in GitHub Desktop.
Save cbenard/8558b1b82359a70df661c17efe1f99d4 to your computer and use it in GitHub Desktop.
Bathroom Fan - Auto Control by Humidity
blueprint:
name: Bathroom Fan - Auto Control by Humidity
description: >
Automatically turns on a bathroom fan when humidity spikes quickly, and turns it off
after humidity stabilizes for a set time. Manual overrides are respected. Optionally
turns off the fan after it's been on for a maximum time if the humidity is also flat.
domain: automation
author: Chris Benard (assisted by ChatGPT)
input:
humidity_rate_fast:
name: Fast Humidity Rate Sensor
description: Derivative sensor with short window (e.g. 2min)
selector:
entity:
domain: sensor
humidity_rate_slow:
name: Slow Humidity Rate Sensor
description: Derivative sensor with long window (e.g. 10min)
selector:
entity:
domain: sensor
fan:
name: Fan Entity
selector:
entity:
domain: fan
spike_threshold:
name: Spike Rate Threshold (%/min)
description: Rate of humidity rise that triggers fan (e.g. 0.25)
default: 0.25
selector:
number:
min: 0.01
max: 2.0
step: 0.01
mode: slider
flat_threshold:
name: Flat Rate Threshold (%/min)
description: Max rate of change considered “flat” (e.g. 0.05)
default: 0.05
selector:
number:
min: 0.001
max: 1.0
step: 0.001
mode: slider
flat_duration:
name: Flat Duration (minutes)
description: How long the humidity must stay flat before turning off
default: 30
selector:
number:
min: 1
max: 180
step: 1
unit_of_measurement: minutes
enable_max_runtime:
name: Also turn off fan if it’s been on too long and humidity is flat
default: false
selector:
boolean: {}
max_runtime:
name: Max Fan Runtime (minutes)
description: Only applies if the above is checked
default: 120
selector:
number:
min: 5
max: 1440
step: 1
unit_of_measurement: minutes
mode: restart
trigger:
- id: humidity_spike
platform: numeric_state
entity_id: !input humidity_rate_fast
above: !input spike_threshold
- id: fan_on_too_long
platform: state
entity_id: !input fan
to: "on"
for:
minutes: !input max_runtime
enabled: !input enable_max_runtime
action:
- if:
- condition: trigger
id: humidity_spike
then:
- service: fan.turn_on
target:
entity_id: !input fan
- variables:
flat_threshold_value: !input flat_threshold
humidity_rate_slow_entity: !input humidity_rate_slow
flat_duration_value: !input flat_duration
- wait_for_trigger:
- platform: template
value_template: >
{% set rate = states(humidity_rate_slow_entity) | float(0) %}
{{ rate | abs < flat_threshold_value | float }}
for:
minutes: "{{ flat_duration_value | int }}"
- condition: state
entity_id: !input fan
state: "on"
- service: fan.turn_off
target:
entity_id: !input fan
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment