diff --git a/config/packages/alarm.yaml b/config/packages/alarm.yaml index d2c59990..97759d9f 100755 --- a/config/packages/alarm.yaml +++ b/config/packages/alarm.yaml @@ -256,12 +256,14 @@ automation: condition: - condition: template - value_template: "{{ states('climate.downstairs') != 'off' }}" + value_template: >- + {{ states('climate.downstairs') != 'off' + or states('climate.upstairs') != 'off' }} action: - - service: climate.turn_off + - service: script.reconcile_hvac_state data: - entity_id: climate.downstairs + reason: "entry point left open" - service: script.speech_engine data: value1: >- @@ -285,29 +287,10 @@ automation: for: minutes: 5 - condition: - - condition: template - value_template: "{{ states('climate.downstairs') == 'off' }}" - action: - - service: climate.turn_on + - service: script.reconcile_hvac_state data: - entity_id: climate.downstairs - - choose: - - conditions: - - condition: numeric_state - entity_id: sensor.pirateweather_temperature - below: 75 - sequence: - - service: script.send_to_logbook - data: - topic: "CLIMATE" - message: "Skipping downstairs cool mode (outside temp <75F)." - default: - - service: climate.set_hvac_mode - data: - entity_id: climate.downstairs - hvac_mode: cool + reason: "entry points secured" #-------------------------------------------#------------------------------------------- - alias: 'Alarm lights in Living room' @@ -332,8 +315,8 @@ automation: action: - choose: - conditions: > - {{ states.group.entry_points.state == 'on' or - states.group.garage_doors.state != 'closed' }} + {{ is_state('group.entry_points', 'on') or + not is_state('group.garage_doors', 'closed') }} sequence: - service: scene.turn_on entity_id: scene.Red_living_Room diff --git a/config/packages/climate.yaml b/config/packages/climate.yaml index d794ae4a..3299cb95 100644 --- a/config/packages/climate.yaml +++ b/config/packages/climate.yaml @@ -207,128 +207,6 @@ script: entity_id: input_datetime.hvac_condenser_lines_cleaning_snooze_until datetime: "{{ (now() - timedelta(minutes=1)).strftime('%Y-%m-%d %H:%M:%S') }}" - set_downstairs_target_temp_based_on_conditions: - alias: Set Downstairs Target Temperature Based on Conditions - mode: single - sequence: - - choose: - - conditions: - - condition: state - entity_id: group.family - state: 'not_home' - sequence: - - service: script.send_to_logbook - data: - topic: "CLIMATE" - message: "Downstairs HVAC set to ECO (family not_home)." - - service: climate.set_preset_mode - data: - entity_id: climate.downstairs - preset_mode: 'eco' - - conditions: - - condition: and - conditions: - - condition: state - entity_id: group.family - state: 'home' - - condition: template - value_template: >- - {{ states('sensor.pirateweather_temperature') in ['unknown','unavailable','none',''] }} - sequence: - - service: script.send_to_logbook - data: - topic: "CLIMATE" - message: "Outside temp unavailable; allowing downstairs cool mode (defaulting to 80F)." - - service: climate.set_hvac_mode - data: - entity_id: climate.downstairs - hvac_mode: cool - - service: climate.set_temperature - data: - entity_id: climate.downstairs - temperature: 80 - - - conditions: - - condition: and - conditions: - - condition: state - entity_id: group.family - state: 'home' - - condition: numeric_state - entity_id: sensor.pirateweather_temperature - below: 78 - sequence: - - service: script.send_to_logbook - data: - topic: "CLIMATE" - message: "Downstairs target set to 78F (family home, outside temp <78F)." - - service: climate.set_hvac_mode - data: - entity_id: climate.downstairs - hvac_mode: cool - - service: climate.set_temperature - data: - entity_id: climate.downstairs - temperature: 78 - - conditions: - - condition: and - conditions: - - condition: state - entity_id: group.family - state: 'home' - - condition: numeric_state - entity_id: sensor.pirateweather_temperature - above: 92 - sequence: - - service: script.send_to_logbook - data: - topic: "CLIMATE" - message: "Downstairs target set to 78F (family home, temp >92F)." - - service: climate.set_hvac_mode - data: - entity_id: climate.downstairs - hvac_mode: cool - - service: climate.set_temperature - data: - entity_id: climate.downstairs - temperature: 78 - - conditions: - - condition: and - conditions: - - condition: state - entity_id: group.family - state: 'home' - - condition: template - value_template: "{{ states('sensor.pirateweather_temperature')|float(-999) >= 78 }}" - sequence: - - service: script.send_to_logbook - data: - topic: "CLIMATE" - message: "Downstairs target set to 80F (family home)." - - service: climate.set_hvac_mode - data: - entity_id: climate.downstairs - hvac_mode: cool - - service: climate.set_temperature - data: - entity_id: climate.downstairs - temperature: 80 - - set_downstairs_daytime_target: - alias: Set Downstairs Daytime Target - mode: single - sequence: - - service: script.set_downstairs_target_temp_based_on_conditions - - set_downstairs_hvac_cool: - alias: Set Downstairs HVAC Cool - mode: single - sequence: - - service: climate.set_hvac_mode - data: - entity_id: climate.downstairs - hvac_mode: cool - set_upstairs_cool_82: alias: Set Upstairs Cool 82 mode: single @@ -349,6 +227,7 @@ script: ############################################################################## automation: - alias: Notify Climate Filter Change Due + id: notify_climate_filter_change_due description: Notify when HVAC filter runtime exceeds the location threshold or age reaches 9 months trigger: - platform: numeric_state @@ -658,7 +537,9 @@ automation: entity_id: binary_sensor.powerwall_grid_status state: 'on' action: - - service: script.set_downstairs_daytime_target + - service: script.reconcile_hvac_state + data: + reason: daytime target refresh # Set thermostats to eco mode when everyone is away - alias: 'Set Thermostats to Eco When Away' @@ -676,26 +557,9 @@ automation: entity_id: input_boolean.guest_mode state: 'off' action: - - service: climate.set_preset_mode + - service: script.reconcile_hvac_state data: - entity_id: climate.downstairs - preset_mode: 'eco' - - choose: - - conditions: - - condition: numeric_state - entity_id: sensor.pirateweather_temperature - below: 75 - sequence: - - service: script.send_to_logbook - data: - topic: "CLIMATE" - message: "Skipping downstairs cool mode (outside temp <75F)." - default: - - service: script.set_downstairs_hvac_cool - - service: climate.set_temperature - data: - entity_id: climate.upstairs - temperature: 83 + reason: family away # Automation: Set Thermostats Back to Cool Mode - alias: 'Set Thermostats to Cool When Home' @@ -717,19 +581,9 @@ automation: entity_id: binary_sensor.powerwall_grid_status state: 'on' action: - - service: climate.set_preset_mode + - service: script.reconcile_hvac_state data: - entity_id: climate.downstairs - preset_mode: 'none' - - service: climate.set_hvac_mode - data: - entity_id: climate.upstairs - hvac_mode: cool - - service: script.set_downstairs_target_temp_based_on_conditions - - service: climate.set_temperature - data: - entity_id: climate.upstairs - temperature: 82 + reason: family home - alias: 'Reset Upstairs to 82 Each Night' id: reset_upstairs_thermostat_nightly_82 @@ -765,6 +619,9 @@ automation: value_template: "{{ state_attr('climate.downstairs', 'hvac_action') == 'idle' }}" - condition: template # Never run if the grid is down and running on powerwall. value_template: "{{ states('binary_sensor.powerwall_grid_status')|lower == 'on' }}" + - condition: state + entity_id: group.entry_points + state: 'off' action: - choose: - conditions: @@ -790,5 +647,7 @@ automation: entity_id: climate.downstairs temperature: 77 - delay: "00:20:00" - - service: script.set_downstairs_target_temp_based_on_conditions + - service: script.reconcile_hvac_state + data: + reason: humidity cycle complete - delay: "02:00:00" # stops it from being triggered again too soon. diff --git a/config/packages/powerwall.yaml b/config/packages/powerwall.yaml index ead4b3be..78c0a24b 100755 --- a/config/packages/powerwall.yaml +++ b/config/packages/powerwall.yaml @@ -470,11 +470,9 @@ automation: value_template: "{{ states('binary_sensor.powerwall_grid_status') == 'off' }}" action: - - service: climate.turn_off + - service: script.reconcile_hvac_state data: - entity_id: - - climate.downstairs - - climate.upstairs + reason: "grid outage" - service: script.notify_engine data: @@ -494,46 +492,14 @@ automation: for: minutes: 10 - condition: - - condition: template - value_template: "{{ states('binary_sensor.powerwall_grid_status') == 'on' }}" - - condition: or - conditions: - - condition: state - entity_id: climate.downstairs - state: 'off' - - condition: state - entity_id: climate.upstairs - state: 'off' - action: - - choose: - - conditions: - - condition: numeric_state - entity_id: sensor.pirateweather_temperature - below: 75 - sequence: - - service: script.send_to_logbook - data: - topic: "CLIMATE" - message: "Skipping downstairs cool mode (outside temp <75F)." - default: - - service: climate.set_hvac_mode - data: - entity_id: climate.downstairs - hvac_mode: cool - - service: climate.set_hvac_mode - data: - entity_id: climate.upstairs - hvac_mode: cool - - service: climate.set_temperature + - service: script.reconcile_hvac_state data: - entity_id: climate.upstairs - temperature: 80 + reason: "grid restored" - service: script.notify_engine data: title: "Electrical Grid Status {{ (trigger.to_state.state)|replace('True', 'up')|replace('False', 'down') }}." - value1: "All AC systems are set back to normal operations (downstairs cool may be skipped if outside <75F)." + value1: "HVAC settings were reconciled with grid, entry-point, and occupancy conditions." who: 'family' group: 'information' diff --git a/config/script/hvac_control.yaml b/config/script/hvac_control.yaml new file mode 100644 index 00000000..8ac89a0b --- /dev/null +++ b/config/script/hvac_control.yaml @@ -0,0 +1,143 @@ +###################################################################### +# @CCOSTAN - Follow Me on X +# For more info visit https://www.vcloudinfo.com/click-here +# Original Repo : https://github.com/CCOSTAN/Home-AssistantConfig +# ------------------------------------------------------------------- +# HVAC Control - Shared thermostat target and safety reconciliation +# Keeps grid, open-entry, occupancy, guest, and weather rules aligned. +# ------------------------------------------------------------------- +###################################################################### + +set_downstairs_target_temp_based_on_conditions: + alias: Set Downstairs Target Temperature Based on Conditions + mode: restart + sequence: + - choose: + - conditions: + - condition: state + entity_id: group.family + state: 'not_home' + - condition: state + entity_id: input_boolean.guest_mode + state: 'off' + sequence: + - service: script.send_to_logbook + data: + topic: "CLIMATE" + message: "Downstairs HVAC set to ECO (family not_home)." + - service: climate.set_preset_mode + target: + entity_id: climate.downstairs + data: + preset_mode: 'eco' + default: + - variables: + outside_temp: "{{ states('sensor.pirateweather_temperature') | float(none) }}" + target_temp: >- + {% if outside_temp is none %} + 80 + {% elif outside_temp < 78 or outside_temp > 92 %} + 78 + {% else %} + 80 + {% endif %} + - service: climate.set_preset_mode + target: + entity_id: climate.downstairs + data: + preset_mode: 'none' + - service: climate.set_hvac_mode + target: + entity_id: climate.downstairs + data: + hvac_mode: cool + - service: climate.set_temperature + target: + entity_id: climate.downstairs + data: + temperature: "{{ target_temp }}" + - service: script.send_to_logbook + data: + topic: "CLIMATE" + message: >- + Downstairs target set to {{ target_temp }}F + (family/guest occupied; outside={{ outside_temp | default('unavailable', true) }}F). + +reconcile_hvac_state: + alias: Reconcile HVAC State + mode: restart + sequence: + - variables: + reconcile_reason: "{{ reason | default('state change', true) }}" + - choose: + - conditions: + - condition: state + entity_id: binary_sensor.powerwall_grid_status + state: 'off' + sequence: + - service: climate.turn_off + target: + entity_id: + - climate.downstairs + - climate.upstairs + - service: script.send_to_logbook + data: + topic: "CLIMATE" + message: "HVAC kept off because the grid is down ({{ reconcile_reason }})." + - conditions: + - condition: state + entity_id: group.entry_points + state: 'on' + sequence: + - service: climate.turn_off + target: + entity_id: + - climate.downstairs + - climate.upstairs + - service: script.send_to_logbook + data: + topic: "CLIMATE" + message: "HVAC kept off because an entry point is open ({{ reconcile_reason }})." + - conditions: + - condition: state + entity_id: group.family + state: 'not_home' + - condition: state + entity_id: input_boolean.guest_mode + state: 'off' + sequence: + - service: climate.set_preset_mode + target: + entity_id: climate.downstairs + data: + preset_mode: 'eco' + - service: climate.set_hvac_mode + target: + entity_id: climate.upstairs + data: + hvac_mode: cool + - service: climate.set_temperature + target: + entity_id: climate.upstairs + data: + temperature: 83 + - service: script.send_to_logbook + data: + topic: "CLIMATE" + message: "HVAC reconciled to away targets ({{ reconcile_reason }})." + default: + - service: script.set_downstairs_target_temp_based_on_conditions + - service: climate.set_hvac_mode + target: + entity_id: climate.upstairs + data: + hvac_mode: cool + - service: climate.set_temperature + target: + entity_id: climate.upstairs + data: + temperature: 82 + - service: script.send_to_logbook + data: + topic: "CLIMATE" + message: "HVAC reconciled to occupied targets ({{ reconcile_reason }})."