Why does repeat.index in a script with a single loop not start at 1?

I’m pretty stumped.
Is this some known bug? See the screenshot below from traces. It looks like the very first iteration of the repeat loop doesn’t have first: true and also has repeat.index starting at 26?

My script is relatively simple

  - repeat:
      count: "{{ number_of_steps }}"
      sequence:
        - action: light.turn_on
          metadata: {}
          data:
            transition: "{{ ... }}"
            brightness_pct: >-
              {{ some function of repeat.index... }}
            kelvin: >-
              {{ ...ditto... }}
          target:
            entity_id: "{{ light_id }}"
        - delay:
            hours: 0
            minutes: 0
            seconds: "{{ ... }}"
            milliseconds: 100

How do you expect us to help when you have redacted everything from your question?

1 Like

I think the only relevant thing is the structure of the loop.
Is it normal for something labeled as Iteration 1 to have first: false and index: 26. Do the values of some calls to turn_on light really matter? it might as well be just the no-op delay.

Ooh-ooh- I know! :person_raising_hand:
{{…}}
Hope that helps…

2 Likes

And I know you are wrong.

I searched through my available traces to find an example containing a repeat and found just this one. It’s from a repeat until and it behaves as one would expect.

I don’t know what makes your example different.

1 Like

Thanks a lot @123. I use loops in only three of my scripts, and they all behave as expected.

Even this script behaves correctly 99% of the time but would occasionally “randomly” start from some number.

And BTW I’m obviously also not setting the repeat.index variable to anything in my loops, I only read it (i don’t even know if it would work but jinja prob allows it). So it’s pretty bizarre.

I’m doing a few more tests explicitly setting repeat.index it to a variable within each iteration, as that would be much easier to trace.

The only interesting thing I’ve observed in my logs is that the script behaves normally 99% of the time but the few “weird” behavior times when the loop starts from a random number is when it’s invoked consecutively. The run mode is set to “Single” and I don’t see any warnings in the logs that it’s killed but I’m starting to think it could be something related to tightly ordered invocations of the script itself. Still doesn’t make much sense to me. I’ll see what I can find.

The oddest part to me is just not that index isn’t at 1 but that it says first: false. How can the infra mark something as not being first in a script with just a single simple loop. So bizarre…

Mystery solved!

This appears to be purely a visualization bug in the Trace UI itself, the values themselves are accurate (meaning the values of repeat.first and repeat.index

If you have a large number of iterations (it appears anything over 25-ish but may be a diff value), the Traces UI incorrectly resets it to Iteration 1 but displays the 26th and further iteration values. That also explains why it shows first: false which was the most puzzling of all.

@123 do you know if it’s best to report this on the github side and under what topic? I’m fairly certain it’ll just go in a black hole somewhere as it’s not particularly critical :wink:

I suggest posting it as an Issue in the Frontend repository.

1 Like

Noted, thx!

repeat.index does start at 1, automation/script traces will only show you the last 20 iterations which are named iteration 1 through 20.

It’s not a visual bug, it’s by design to reduced the stored information in a trace. Essentially they don’t want people storing 1000’s of iteration information in a single trace.

Showing the last 20 is ok but there is actually a bug because the UI incorrectly label it as Iteration 1 which is mighty confusing IMHO. It should correctly state Iteration X depending on how many iterations are in total and subtract 20 from that total count (if it shows the last 20).

That’s the name of the stored iteration, that does not represent the actual iteration number.

Respectfully, I’d have to disagree with you @petro. We can argue semantics here but something saying “Iteration 1” to me reads as the first iteration rather than "the 1st of some arbitrarily starting number of iterations (specifically Max iterations - 20). It’s extremely confusing IMHO. I’ll post it as a bug as suggested by @123 – fully knowing that 99% likeliehood is no dev will look at it, and if they do, maybe they’ll take your stance. But I think it’s worth reporting.

I’m explaining how it works. There’s nothing to disagree with. It may be misleading but that’s what the actual intention of the name is. To show you the stored iteration in the trace.

Fair and understood.

We don’t currently store how many iterations there were in total. We would need to change that in order for frontend to be aware of it.

If you add it to the backend I’m sure I could convince Tim to add it to the frontend. I could add it too if you’re too busy.

I definitely won’t have the time, and I also think this is a pretty minor problem all things considered. But if you want to give it a go yourself, you are certainly welcome to. :slight_smile:

Edit:
I don’t know how well you know that code, but just in case, here should be a good starting point for this: core/homeassistant/helpers/trace.py at a722912e05c64564e5d95d66a796f3490c496a71 · home-assistant/core · GitHub
We would need to also store the counter in addition to the deque.

1 Like

I’ve never looked at that section but I need to learn it for template traces when I plan to add them. But that’s a year or so out.