Quester Studio

Template syntax

How {{env}}, {{input}}, {{vars}}, {{secrets}}, and {{nodes}} resolve at runtime

String fields in nodes (URLs, headers, bodies, conditions, set values, and output maps) support mustache-style tokens. The engine replaces each {{…}} before the node runs.

The previous node’s JSON is not a template scope. It is already the next node’s execute input — use JMESPath there (body.id, products[0]). See How flows work.

{{env}} {{secrets}} {{input}} {{vars}} {{nodes.id}} Wire / JMESPath sits outside this row — use body.title on extract
Five template roots. Merge also has source keywords previous / input / vars / node ids — those are not mustache scopes.

Scopes

TokenSourceExample
{{env.KEY}}Environment variables{{env.API_BASE}}
{{secrets.KEY}}Secrets file for the selected env{{secrets.API_TOKEN}}
{{input.path}}Flow run input (CLI --input / Run panel){{input.username}}
{{vars.key}}Variables set by set nodes{{vars.token}}
{{nodes.id}}Full output of a prior node{{nodes.login}}
{{nodes.id.path}}Nested field on a prior node output{{nodes.login.body.id}}

Missing paths resolve to an empty string ("").

Run input vs wire vs input node

NeedUse
Field from Run panel / --input in a string{{input.email}}
Put that payload on the wire for the next nodeinput node
Field from the last step inside extract/assert/jsonJMESPath body.id
Field from a named earlier node in a string{{nodes.httpId.body.id}}
Combine bagsmerge sources: ["previous", "input", …]

Dot paths

{{input.profile.age}}
{{nodes.login.body.user.id}}
{{env.API_BASE}}

Examples

URL and headers

{
  "method": "GET",
  "url": "{{env.API_BASE}}/users/{{nodes.userId}}",
  "headers": {
    "Authorization": "Bearer {{secrets.API_TOKEN}}"
  }
}

JSON body as a string

{
  "method": "POST",
  "url": "{{env.API_BASE}}/users",
  "headers": { "Content-Type": "application/json" },
  "body": "{\"username\": \"{{input.username}}\", \"email\": \"{{input.email}}\"}"
}

Object body

{
  "body": {
    "username": "{{input.username}}",
    "token": "{{secrets.API_TOKEN}}"
  }
}

Conditions (if)

{
  "type": "if",
  "data": {
    "condition": "{{input.active}}",
    "checks": [{ "path": "status", "op": "gte", "value": 200 }]
  }
}

checks[].path is JMESPath on the wire (e.g. status after HTTP).

set variables

{
  "type": "set",
  "data": {
    "variables": {
      "greeting": "Hello {{input.username}}",
      "retryCount": 3
    }
  }
}

Template node vs {{…}}

  • {{…}} tokens — string substitution in templated fields.
  • template node — also supports Eta (<%= it.input.name %>, <%= it.previous %>) after mustache resolution. See template node.

JMESPath (wire, not mustache)

extract, transform, assert, and json query the previous node output with JMESPath:

GoalExpression
HTTP body idbody.id
First productbody.products[0]
Nested namebody.user.name