WTH isn't there an if-elif-else instead of choose

Continuing the discussion from WTH. Script execution stops after a condition step in script sequence, rather than continue past:

Iā€™m beginning to believe that the choose construct was a mistake. :laughing: :cry: It seems to confuse everyone.

I think this would be better (and now that Iā€™ve had a chance to think about it more, it wouldnā€™t really be any more difficult to implement than choose was):

- if:
  <conditions>
  then:
  <actions>
- elif:
  <conditions>
  then:
  <actions>
- else:
  <actions>

where <conditions> are one or more conditions:

- if:
  - condition: state
    entity_id: binary_sensor.abc
    state: 'on'
  - condition: template
    value_template: "{{ abc == '123' }}"

and <actions> are one or more actions:

  then:
  - service: script.abc
  - event: xyz

and elif and else are both optional, meaning you could use one, or the other, or both, or neither.

5 Likes

So if no condition is true no action is performed without generating an error?

I raelly liked how elegant this solution this was:

But it would work just as well with if / else.

Why would there be an error? Yes, ā€œif FALSE then Xā€ would mean donā€™t do X. Why is that unclear in any way?

The elegant solution you linked to (if ā€œif-elif-elseā€ was available as I proposed), would just look like this instead (but would be exactly equivalent):

- id: light_dependency
  alias: Light dependency
  description: "Switch lights to same state"
  trigger:
    platform: state
    entity_id: light.patio
  action:
    - if:
        - condition: template
          value_template: "{{ trigger.to_state.state == 'on' }}"
      then:
        - service: light.turn_on
          entity_id:
            - light.garden
    - elif:
        - condition: template
          value_template: "{{ trigger.to_state.state == 'off' }}"
      then:
        - service: light.turn_off
          entity_id:
            - light.garden

Think jinja. Iā€™ve lost count of the number of times Iā€™ve told people they need an else case to cover all eventualities.

Thatā€™s totally different. If youā€™re using service_template, then the template must provide a service, because youā€™re basically saying ā€œcall a service, but let me figure out which one first.ā€ But an if action is only doing something if the conditions are true. Itā€™s the difference between:

Do X if Y

vs

If X do Y

In the former (which is like a service_template), if X is false then youā€™ve said do something, but did not provide what to do.

In the latter (which is like an if action), if X is false then you havenā€™t said to do anything.

1 Like

Iā€™m trying to think this trough. Iā€™m creating a pseudocode choose, adding if, then, else statements as comments. That is easier for me to think about them that way.

- choose:
    - conditions: # If
        <user is Phil>
      sequence: # then
        <Phil's action>
    - conditions: # elseif
        <user is Tom>
      sequence: # then
        <Tom's action>
  default: #else, then
    <Alternate user action>

Yes, a choose action can be used like if-elif-else. In fact, thatā€™s what it really is. But it seems to confuse a lot of people. Iā€™m not sure why, but it does.

The structure isnā€™t not obvious, the indents seem inconsistent. I think choose is one I will always have to copy reference code to get started. I donā€™t think I will ever get it right if I try to type it manually. For example it breaks my brain that default is at a different level than the conditions. My brain wants the else to be at the same level as the elseif's.

5 Likes

Maybe my example would look like this?

- if:
    - conditions:
        <user is Phil>
      then:
        <Phil's action>
    - conditions:
        <user is Tom>
      then:
        <Tom's action>
    - else:
        <Alternate user action>

Or the else could look like this?

    - else:
      then:
        <Alternate user action>

Not based on what Iā€™m proposing. It would be:

- if:
    <user is Phil>
  then:
    <Phil's action>
- elif:
    <user is Tom>
  then:
    <Tom's action>
- else:
    <Alternate user action>
4 Likes

So we could omit the - conditions: and just get to a condition. If thatā€™s possible, that would be nice. But either works in my mind.

:heart: this

I try to live by the motto, ā€œItā€™s never too lateā€ :slight_smile: But I realize that once published and people start using it, itā€™s super painful to pull it back. So I guess we live with it and just document. Or could if / else be introduced as aliases for conditions to get most of the way there?

IMO, eliminating the duplicated items would be even more ā€œelegantā€. I know this isnā€™t valid yaml, but Iā€™m thinking of something like:

- id: light_dependency
  alias: Light dependency
  description: "Switch lights to same state"
  trigger:
    platform: state
    entity_id: light.patio
  action:
    entity_id:
      - light.garden
    if:
      - condition: template
        value_template: "{{ trigger.to_state.state == 'on' }}"
      - then:
        - service: light.turn_on
      - else:
        - service: light.turn_off

As for why choose confuses people, for me itā€™s the conditions: part. I only see one mention of it in the documentation: Script Syntax - Home Assistant and it is super simple. It isnā€™t clear to me from it how multiple conditions would work - are they AND or OR? And how do multiple ELSEā€™s fit into the example? And separately, despite having programmed in various languages off and on for 40 years, I canā€™t wrap my head around how the else in the example makes sense given the indention. Course, Iā€™m still not a yaml expert, so that may be part of the problem (for me and others).

Perhaps the ā€œelegantā€ example could be added to the documentation, and maybe the example in the 0.113 notes (or point to that example) as well. In both cases, a few comments pointing out the parallel to if, elsif, else would go a long, long ways.

Mostly unrelated, but I just noticed it isnā€™t mentioned on the automations documentation page, only the scripts page.

2 Likes

Follow the link to the conditions page and it explains it there, because itā€™s the same everywhere multiple conditions are accepted. It canā€™t be explained over and over again everywhere. That would not be maintainable.

Yep, thatā€™s definitely part of the problem for new users.

Itā€™s definitely on my to-do list to enhance the documentation for the choose action.

Itā€™s on the ā€œscript syntaxā€ page, which is used by both the scriptā€™s sequence section and the automationā€™s action section. (An automation is really nothing but a script with trigger/condition tacked on to decide when to automatically run the actions.) I have a PR somewhere in the stages of release that reorganizes the script & automation pages somewhat to make it clearer, but itā€™s stuck somewhereā€¦

1 Like

And a quick link to the preview.

2 Likes