Skip to main content
The Loop node repeats a set of steps. It supports three iteration modes: forEach, while, and times.

Loop modes

ForEach

Iterates over each item in an array. The current item and index are available to nodes inside the loop body.

While

Repeats as long as a condition is true. Evaluates the condition before each iteration.

Times

Repeats a fixed number of times.

Output handles

Accessing loop variables

Inside the loop body, two special variables are injected on each iteration: You can customize these names in the loop node properties panel. Use them in any template expression inside the loop body:
When {{ item }} is the entire value (not mixed with other text), the original type is preserved. For example, if item is an object, {{ item }} resolves to that object, not a JSON string. When mixed with text like https://api.com/{{ item.id }}, it resolves to a string.

Example: Fetch users and post each to a webhook

This example fetches a list of users from an API, then loops over each user and sends their data to a webhook.

Canvas layout

Step 1: Fetch Users (Connector node, direct mode)

Step 2: Loop (forEach)

The array path users.data navigates into the HTTP response: users (output variable) is the parsed HTTP response object { data, status, headers, statusText }, and .data is the response body (here a JSON array of user objects).

Step 3: Post to Webhook (Connector node inside loop body, direct mode)

On each iteration, {{ item }} resolves to the current user object (e.g., {"id": 1, "name": "Leanne Graham", "email": "Sincere@april.biz", ...}). You can also map individual fields:

Step 4: Send Summary (Connector node after loop completes)

Connect from the loop’s Complete handle. This node runs once after all iterations are finished. The loop’s collected results are available via its output variable.

When an item fails

With Continue with the next item, a failed iteration leaves { "error": { "message", "code" }, "index" } in its slot of the loop’s result array instead of a value, and the failures alone are available as {{ result_<node id>_failures }}, a list of { index, message, code }. The loop’s node id is shown under the setting, so for a node with id loop-1 the variables are {{ result_loop-1 }} and {{ result_loop-1_failures }}. Nodes after the loop can act on either, for example to email the rows that did not import. The run still finishes as Failed, with the count and the first failure in its error, so an ERROR notification rule reports partial imports the same way as total ones. Some failures stop the run whatever this setting says, because they are decisions about the run rather than about one item: a Cancel node, an approval that was rejected, the account running out of credits, and the per-run attachment download cap. Use it for per-row imports where one bad row must not block the rest. Pair it with a lookup that skips rows already imported, so a re-run after fixing the bad rows does not create duplicates.

Tips

  • Always set a max iterations limit on while loops to prevent runaway execution.
  • The loop collects results from each iteration; the complete output is an array of all iteration results.
  • For parallel processing of array items, consider using a Parallel node instead.