For Loops
A for loop runs its block once per element of a source: a numeric range, or the rows of a query result. It is the construct for "do something with each row" logic - per-row writes, running totals, anything a single pipeline cannot express - without leaving RQL. Like all control flow, it runs inside the request's one transaction.
Over a numeric range
gen::series(from, to) yields the integers from through to, inclusive, as a loop source. The loop variable is an ordinary variable inside the block; state accumulates through reassignment. Run the snippets on this page in order:
Over query results
To iterate rows, first bind the query to a frame variable with let, then loop over it. Inside the block, each row's columns are reachable as fields on the loop variable ($row.qty):
The binding step is required. Putting the query inline in the loop header is a parse error - for iterates variables and ranges, not subqueries:
Loops that write
The block can contain any statement, including writes. Combined with an if guard, a for loop becomes a per-row dispatch: inspect each row, act on the ones that qualify. Every write in the loop commits atomically with the rest of the request:
for or something else?
- --Known element count or a row set:
for. Repeating until a condition flips: a while loop. - --Exit or skip decided mid-block: a loop with break and continue.
- --A per-row transformation with no side effects: not a loop at all - a
mapover the pipeline says the same thing declaratively and lets the engine do the iterating.
gen::series feeds for loops; it is not a table and cannot be queried with from. To iterate rows, query them and bind the result to a frame variable first.