<isolate>
and <call>
<isolate>
and <call>
define or invoke,
respectively, block logic that cannot capture values from an enclosing context.
Using the unnamed form: <isolate>
It is often useful to separate small pieces of logic within a larger whole. In the most
basic case, the <isolate>
block form provides a space to perform a
logical task without imposing any side effects on the block within which it appears:
Works
<defblock name="outer" outer_variable="1.61803"> <isolate inner_variable="3.14159"> <willbe name="inner_col" value="round({@inner_variable};1)"/> </isolate> <willbe name="outer_col" value="round({@outer_variable};1)"/> </defblock> <call block="outer"/>
<isolate>
form is used to:- Create a new variable called inner_variable
- Set the value of inner_variable to a value
- Use the local variable to compute a new column
It should be noted that the variable defined in the opening tag of the
<isolate>
element is only accessible inside the nested
<isolate>
form. If outer_variable
is referenced
within the <isolate>
an error will be returned:
Returns an error: Syntax error: Undefined @variable referred to in: round({@outer_variable};1)
<defblock name="outer" outer_variable="1.61803">
<isolate inner_variable="3.14159">
<willbe name="inner_col" value="round({@inner_variable};1)"/>
<!--This willbe returns an error because <isolate> does not have access to @outer_variable-->
<willbe name="outer_col" value="round({@outer_variable};1)"/>
</isolate>
</defblock>
<call block="outer"/>
Conversely, the outer <defblock>
does not have access to the variable
defined by <isolate>
. In the following example an error will be
returned:
Returns an error: Syntax error: Undefined @variable referred to in: round({@inner_variable};1)+1
<defblock name="outer" outer_variable="1.61803">
<isolate inner_variable="3.14159">
<willbe name="inner_col" value="round({@inner_variable};1)"/>
</isolate>
<!--This willbe returns an error because the outer <defblock> does not have access to @inner_variable-->
<willbe name="inner_col_add_one" value="round({@inner_variable};1)+1"/>
</defblock>
<call block="outer"/>
Invoking a named block with <call>
The <call>
operation can be used to invoke a named
<block>
or <defblock>
within another block form
and produce the same behavior as <isolate>
. In the next example, two
non-nested <defblock>
forms are created. inner_block
is
called inside outer_block
, but only access variables defined in its own
context. The example below runs without error and creates two new columns.
<defblock name="inner_block" inner_variable="3.14159"> <willbe name="inner_col" value="round({@inner_variable};1)"/> </defblock> <defblock name="outer_block" outer_variable="1.61803"> <willbe name="outer_col" value="round({@outer_variable};1)"/> <call block="inner_block"/> </defblock> <call block="outer_block"/>
Conversely, if inner_block
attempts to access a variable defined in
outer_block
, or vice versa, running the query will result in an
error:
Returns the error: Syntax error: Undefined @variable referred to in: round({@inner_variable};1)
<defblock name="inner_block" inner_variable="3.14159"> <willbe name="inner_col" value="round({@inner_variable};1)"/> <!--An error is throw because the block can't access @inner_variable--> </defblock> <defblock name="outer_block" outer_variable="1.61803"> <willbe name="outer_col" value="round({@inner_variable};1)"/> <!--An error is throw because the block can't access @inner_variable--> <call block="inner_block"/> </defblock> <call block="outer_block"/>
If it is necessary to use a variable defined in outer_block
within
inner_block
, the desired result can be achieved with call by explicitly
defining a parameter in inner_block
and passing
outer_variable
to the inner_block
with
<call/>
:
<defblock name="inner_block" inner_variable="3.14159" capture_outer=""> <willbe name="inner_col" value="round({@captured_outer};1)"/> </defblock> <defblock name="outer_block" outer_variable="1.61803"> <willbe name="outer_col" value="round({@outer_variable};1)"/> <call block="inner_block" captured_outer="{@outer_variable}"/> </defblock> <call block="outer_block"/>
The method above is the best practice for exchanging variables between named blocks.