{let $first: 10 /} // this is a single line soy comment
{if $first > 5 }
{$first}<br/>
{let $first:$first-1 /}
{/if}
{$first}
I tried this, and it prints: 10 10
Ideally, it should print: 10 9 ..
Can you please identify what's wrong in my code?
First of all, you cannot really overwrite the value of $first
. The documentation states local variables defined by let
are not modifiable. This is because whenever you alias a value with let
, a new variable is created in the compiled output. Moreover, the scoping rules of soy expressions aren't the same as in Javascript (but you could think of {let}
having similar semantics to ECMAScript 6's let
statement, that is, non-hoisted, block-scoped).
In your code:
{let $first: 10 /} /* 1 */
{if $first > 5}
{$first}<br/>
{let $first¹: $first-1 /} /* 2 */
/* 3 */
{/if}
{$first} /* 4 */
what's happening is:
In (1), $first
is an alias for the value 10
. A variable is introduced to hold this value.
In (2):
Right hand: $first
takes its value from (1), because it is defined in a parent block.
Left hand: $first¹
is being aliased to the value resulting from $first
- 1 = 10 - 1 = 9. Because the definition of $first
can't be overwritten, a new variable is introduced, different from (1). There are two things to note:
a. The value for $first¹
is 9, but it's never read in this snippet.
b. $first¹
only "lives" within the block it was defined, that is, inside {if...}
. In fact, if you were to insert {$first}
in (3), it would output 9.
In (4), the value of $first¹
, being out of the scope introduced by the {if}
block, can no longer be read, so $first
from (1) is the only one visible, yielding 10. It makes use of the same variable as (1) in the compiled output.