How to use context

By checking three conditions you can tell if it was an automation, a physical device or a person performing an action in a dashboard that changed an entity. This can be useful if you need to know if a person or an automation did something, e.g. were the lights turned on automatically or by a person operating a physical switch or dashboard control?

The three context ids and how they relate to the three causes are:

9f58d4c26ecbf53ddbb35cca88956ede8502da41

User mbuscher provided this automation to demonstrate its use, it will generate a log of what caused a switch to turn on or off:

trigger:
  - platform: state
    entity_id:
      - switch.office
    not_to:
      - unknown
      - unavailable
action:
  - choose:
      - conditions:
          - condition: template
            value_template: '{{ trigger.to_state.context.id != none }}'
          - condition: template
            value_template: '{{ trigger.to_state.context.parent_id == none }}'
          - condition: template
            value_template: '{{ trigger.to_state.context.user_id == none }}'
        sequence:
          - service: system_log.write
            data:
              level: debug
              message: Physical device
  - choose:
      - conditions:
          - condition: template
            value_template: '{{ trigger.to_state.context.id != none }}'
          - condition: template
            value_template: '{{ trigger.to_state.context.parent_id == none }}'
          - condition: template
            value_template: '{{ trigger.to_state.context.user_id != none }}'
        sequence:
          - service: system_log.write
            data:
              level: debug
              message: HA user interface
  - choose:
      - conditions:
          - condition: template
            value_template: '{{ trigger.to_state.context.id != none }}'
          - condition: template
            value_template: '{{ trigger.to_state.context.parent_id != none }}'
          - condition: template
            value_template: '{{ trigger.to_state.context.user_id == none }}'
        sequence:
          - service: system_log.write
            data:
              level: debug
              message: HA automation

asterix There are some exceptions though. context.parent_id is only available for automations with triggers that have an identifiable parent entity or device so:




A practical example of use:


.

For each of my rooms I have an input select that stores if the lights for that room are in ā€˜Automatic’ or ā€˜Manual’ scene mode. If someone presses a physical light switch in a room the scene mode for that room changes to ā€˜Manual’ and sends me an actionable notification asking if I would like to change the mode back to ā€˜Automatic’. Until this happens motion lights will no longer be active for this room as the motion lights automation has a condition that checks the input select is in ā€˜Automatic’ mode.

Here is the automation for detecting the physical button press and changing the input select . This has been truncated, there are a lot more rooms & triggers, other scene types too that have been omitted here for clarity. The main thing to note are the context conditions:

- id: 68e2bb6b-ac35-4013-81aa-5e631dfd99fc
  alias: 'Lights to Manual Mode'
  mode: parallel
  max: 10
  trigger:
  - id: bathroom_scene
    platform: state
    entity_id: 
    - light.bathroom_light
    not_from:
      - unavailable
      - unknown
    not_to:
      - unavailable
      - unknown
  - id: cinema_scene
    platform: state
    entity_id:
    - light.cinema
    not_from:
      - unavailable
      - unknown
    not_to:
      - unavailable
      - unknown
  - id: workshop_scene
    platform: state
    entity_id:
    - light.electronics_workshop
    - light.mechanical_workshop
    not_from:
      - unavailable
      - unknown
    not_to:
      - unavailable
      - unknown
  condition:
  - condition: template ### Not in manual mode already? ###
    value_template: "{{ not is_state('input_select.'~ trigger.id, 'Manual') }}"
  - condition: template  ### This is the required 'context', only physical activation of light pass here ###
    value_template: "{{ trigger.to_state.context.id != none }}"
  - condition: template
    value_template: "{{ trigger.to_state.context.parent_id == none }}"
  - condition: template
    value_template: "{{ trigger.to_state.context.user_id == none }}"
  action:
  - service: input_select.select_option
    target:
      entity_id: "{{ 'input_select.'~ trigger.id }}"
    data:
      option: 'Manual'
  - service: notify.telegram_system
    data:
      title: 'šŸ’” <b>Light Mode Changed</b>'
      message: "{{ trigger.id|replace('_scene','')|replace('_',' ')|title }} changed to manual mode."
      data:
        inline_keyboard: "Back to Automatic?:/{{ trigger.id }}"

Examples of motion light automation:

- id: 364b9af0-4147-4f09-a740-e36de92dbb2f
  alias: 'Mechanical Workshop Lights Auto On'
  mode: single
  max_exceeded: silent
  trigger:
  - platform: state
    entity_id: binary_sensor.pir_workshop
    from: 'off'
    to: 'on'
  condition:
  - condition: state
    entity_id: input_select.workshop_scene  ### Note this must be 'Automatic' to pass
    state: 'Automatic'
  - condition: state
    entity_id: light.mechanical_workshop
    state: 'off'
  action:
    service: light.turn_on
    data:
      entity_id: 
      - light.mechanical_workshop
      brightness: 255

- id: e428d821-5e20-439f-a831-2ebf97a14bbe
  alias: 'Mechanical Workshop Lights Auto Off'
  trigger:
  - platform: state
    entity_id: binary_sensor.pir_workshop
    to: 'off'
    for:
      minutes: 6
  condition:
  - condition: state
    entity_id: input_select.workshop_scene  ### Note this must be 'Automatic' to pass
    state: 'Automatic'
  - condition: state
    entity_id: light.mechanical_workshop
    state: 'on'
  action:
    service: light.turn_off
    entity_id: light.mechanical_workshop
13 Likes

I really like the idea/concept and I’ve been thinking for a similar ā€˜automation on/manual override’ switch per room for some time and so far my biggest gap was the ability to switch back to ā€˜automatic mode’ once manual is no longer needed.
Question for the practical use - doesn’t the actionable notification become a bottleneck of sorts? In a multi user house hold I don’t want to be the single person responsible for automations being switched back to enabled.

1 Like

Yeah that could be a problem for other households but I live alone and I rarely ever touch a light switch. I’ve got the automation perfect for me. On the rare occasion I need to go manual it is easy for me to switch back with the notification action.

The mode is mainly for my guests. They like to touch switches. So I let them do what they like. Then when they’re gone I can change all the light modes back at once with another button and script:

Screenshot 2024-04-29 at 21-21-18 Overview – Home Assistant
.

For other use cases you could switch back to manual after a fixed time:

trigger:
  - platform: state
    entity_id: input_select.workshop_scene
    to: 'Manual'
    for:
      hours: 4
action:
  - service: input_select.select_option
    target:
      entity_id: input_select.workshop_scene
    data:
      option: 'Automatic'
2 Likes

This was extremely helpful, I simplified the logic a bit since I don’t need a toggle (I just re-enable the automations in my morning script) and made it more generic so that if I need to disable more automations, I can just extend this automation with more triggers and condtions

alias: Disable Automations
description: ""
triggers:
  - trigger: state
    entity_id:
      - climate.bedjet
    to: "off"
    id: Bedjet off
conditions: []
actions:
  - choose:
      - conditions:
          - condition: trigger
            id:
              - Bedjet off
          - condition: template
            value_template: >-
              {{trigger.to_state.context.id != none and
              trigger.to_state.context.parent_id == none and
              trigger.to_state.context.user_id != none}}
            alias: State changed manually
        sequence:
          - action: automation.turn_off
            metadata: {}
            data:
              stop_actions: true
            target:
              entity_id: automation.master_bed_occupied
        alias: Disable Bed Automation
mode: queued
max: 10

1 Like