Get sibling entities in Python script

Hey all! I hope I’m not trying to solve the wrong problem here. Here goes :slight_smile:

I am writing a python script where I am making decisions about what to do with a device’s entity based on one of its other entity’s states.

I’m basically making a power shedding setup. If my total current is above X, then I want to check each of my relays’ current at the moment and turn one or more of them off until the current is below a threshold. Each relay is a separate esphome device with a current sensor, a relay, and some other entities.

I think what I want to do is this:

  • Given {current_sensor_id}, get the state. If total current > threshold, get the device for {current_sensor_id}.
  • Look at all entities for the device, and find the relay switch. Turn it off.

I see that helpers can do some of this, but it appears they are not accessible from within python scripts.

If there is a better way to do this (preferably without doing string substitution on Ids,) I’m all ears. This is just how I decided to approach it :slight_smile:

Thanks in advance!

That sounds like you could do it in a normal automation or script. Can you post an example device with its set of entities?

How do you decide in what order to check your devices?

Choosing the priority order of entities is a TODO in the code currently :slight_smile:

As a first cut, I want to get the logic working, but eventually I might add an entity to each device to hold the priority or something.

Here is the ESPHome yaml for an instance:

substitutions:
  location: garage
  locationName: Boys' Room
  device: sonoff_minifridge
  deviceName: Mini Fridge
  deviceDescription: Sonoff S31 to control mini fridge
  ipAddress: 192.168.50.107

# import common components
packages:
  common: !include sonoff_switch_template.yaml

And sonoff_switch_template.yaml:

# Basic Config
esphome:
  platform: ESP8266
  board: esp01_1m

# import common components
packages:
  common: !include common/common.yaml

wifi:
  use_address: "$ipAddress"
  manual_ip:
    static_ip: $ipAddress


uart:
  rx_pin: RX
  baud_rate: 4800

binary_sensor:
  - platform: gpio
    pin:
      number: GPIO0
      mode: INPUT_PULLUP
      inverted: True
    name: "$deviceName Button"
    on_press:
      - switch.toggle: relay
  - platform: status
    name: "$deviceName Status"

  - platform: template  # this is to be able to tell if the power shedding logic turned off the switch, and therefore it should be turned back on if/when available current capacity exists again
    name: "$deviceName disabled by shedding"


sensor:
  - platform: wifi_signal
    name: "$deviceName WiFi Signal"
    update_interval: 60s
  - platform: cse7766
    current:
      name: "$deviceName Current"
      accuracy_decimals: 2
      filters:
        - throttle_average: 60s
    voltage:
      name: "$deviceName Voltage"
      accuracy_decimals: 2
      filters:
        - throttle_average: 60s
    power:
      name: "$deviceName Power"
      accuracy_decimals: 2
      id: my_power
      filters:
        - throttle_average: 60s
    energy:
      name: "$deviceName Energy"
      accuracy_decimals: 2
      filters:
        - throttle: 60s
    apparent_power:
      name: "$deviceName Apparent Power"
      filters:
        - throttle_average: 60s
    power_factor:
      name: "$deviceName Power Factor"
      accuracy_decimals: 2
      filters:
        - throttle_average: 60s

  - platform: total_daily_energy #(Optional, not specific to cse7766)
    name: "$deviceName Daily Energy"
    power_id: my_power
    accuracy_decimals: 2

switch:
  - platform: gpio
    name: "$deviceName Relay"
    pin: GPIO12
    id: relay
    restore_mode: RESTORE_DEFAULT_ON

time:
  - platform: sntp #(required for total_daily_energy)
    id: my_time

status_led:
  pin:
    number: GPIO13
    inverted: True

FYI common.yaml includes things like api config, the rest of wifi, ota, etc.

If what I am doing can be done in a normal automation or script, is there a reason I wouldn’t be able to do so in Python?