Skip to content

Commit

Permalink
bug #4169 Fix usage of loop in a for else clause (fabpot)
Browse files Browse the repository at this point in the history
This PR was merged into the 4.x branch.

Discussion
----------

Fix usage of loop in a for else clause

Commits
-------

5649de8 Fix usage of loop in a for else clause
  • Loading branch information
fabpot committed Jul 31, 2024
2 parents ab0c632 + 5649de8 commit 26b6e19
Show file tree
Hide file tree
Showing 3 changed files with 70 additions and 3 deletions.
2 changes: 1 addition & 1 deletion src/Runtime/LoopContext.php
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ public function getParent(): mixed

public function getRevindex0(): int
{
return $this->loop->getLength('revindex0') - $this->getIndex();
return max(0, $this->loop->getLength('revindex0') - $this->getIndex());
}

public function getRevindex(): int
Expand Down
9 changes: 7 additions & 2 deletions src/Runtime/LoopIterator.php
Original file line number Diff line number Diff line change
Expand Up @@ -74,8 +74,8 @@ public function next(): void
public function rewind(): void
{
$this->seq->rewind();
$this->previous = ['valid' => false, 'key' => null, 'value' => null];
if ($this->seq->valid()) {
$this->previous = ['valid' => false, 'key' => null, 'value' => null];
$this->current = ['valid' => $this->seq->valid(), 'key' => $this->seq->key(), 'value' => $this->seq->current()];
} else {
// EmptyIterator
Expand Down Expand Up @@ -123,7 +123,12 @@ public function getNext(): array
{
if (!$this->next) {
$this->seq->next();
$this->next = ['valid' => $this->seq->valid(), 'key' => $this->seq->key(), 'value' => $this->seq->current()];
if ($this->seq->valid()) {
$this->next = ['valid' => $this->seq->valid(), 'key' => $this->seq->key(), 'value' => $this->seq->current()];
} else {
// EmptyIterator
$this->next = ['valid' => false, 'key' => null, 'value' => null];
}
}

return $this->next;
Expand Down
62 changes: 62 additions & 0 deletions tests/Fixtures/tags/for/loop_in_else.test
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
--TEST--
"for" tag loop behavior in an else clause
--TEMPLATE--
{% for item in [] %}
{% else %}
{{ loop.previous is null ? 'OK' : 'KO' }}
{{ loop.next is null ? 'OK' : 'KO' }}
{{ loop.first ? 'OK' : 'KO' }}
{{ loop.last ? 'OK' : 'KO' }}
{{ loop.index0 is same as 0 ? 'OK' : 'KO' }}
{{ loop.revindex0 is same as 0 ? 'OK' : 'KO' }}
{{ loop.length is same as 0 ? 'OK' : 'KO' }}
{{ loop.depth is same as 1 ? 'OK' : 'KO' }}
{% endfor %}

{% for item in empty_it %}
{% else %}
{{ loop.previous is null ? 'OK' : 'KO' }}
{{ loop.next is null ? 'OK' : 'KO' }}
{{ loop.first ? 'OK' : 'KO' }}
{{ loop.last ? 'OK' : 'KO' }}
{{ loop.index0 is same as 0 ? 'OK' : 'KO' }}
{{ loop.depth is same as 1 ? 'OK' : 'KO' }}
{% endfor %}

{% for item in yielding_it %}
{% else %}
{{ loop.previous is null ? 'OK' : 'KO' }}
{{ loop.next is null ? 'OK' : 'KO' }}
{{ loop.first ? 'OK' : 'KO' }}
{{ loop.last ? 'OK' : 'KO' }}
{{ loop.index0 is same as 0 ? 'OK' : 'KO' }}
{{ loop.depth is same as 1 ? 'OK' : 'KO' }}
{% endfor %}
--DATA--
return [
'empty_it' => new \EmptyIterator(),
'yielding_it' => (function (): \Generator { return; yield; })(),
]
--EXPECT--
OK
OK
OK
OK
OK
OK
OK
OK

OK
OK
OK
OK
OK
OK

OK
OK
OK
OK
OK
OK

0 comments on commit 26b6e19

Please sign in to comment.