Skip to main content

Variables & Expressions

Variables are how your chatbot flow remembers information throughout a conversation. When a customer answers a question, when you fetch data from an external system, or when a webhook sends data — all of that is stored in variables that you can use anywhere in the flow.

What are variables?

A variable is a named placeholder that holds a value. For example:

  • {{customer_name}} might hold "Rahul"
  • {{order_total}} might hold "2500"
  • {{selected_product}} might hold "Premium Plan"

You use variables by typing their name inside double curly braces: {{variable_name}}

Where do variables come from?

SourceHow it worksExample variable
SystemAutomatically available in every flow{{customer_name}}, {{customer_phone}}
TriggerPassed by the trigger when the flow starts{{order.catalog_id}}, {{trigger_1.ad.headline}}
Question nodeCustomer types an answer → saved to the variable you specify{{user_email}}, {{order_number}}
HTTP Call nodeExternal system returns data → saved with the node's name as prefix{{http_call_1.status}}, {{http_call_1.result.tracking_url}}
Contact dataGet Details action fetches contact info → saved with a prefix{{lead_name}}, {{lead_email}}
Script nodeScript calculates a result → saved with the node's name as prefix{{script_1.discount_amount}}, {{script_1.final_price}}
Interactive responsesButton clicks and list selections{{button_id}}, {{row_id}}

System variables

These are available in every flow, regardless of trigger type:

VariableDescriptionExample value
{{customer_name}}Customer's name from their WhatsApp profileJohn Doe
{{customer_phone}}Customer's phone number+919876543210
{{initial_message}}The first message the customer sent that triggered the flowHello, I need help
{{whatsapp_message_id}}Unique ID of the triggering WhatsApp messagewamid.HBgLMTY1MDg5...

Last interaction variables

When a customer taps a button or selects a list row, the value is captured in these variables for use in the next nodes:

VariableDescriptionExample value
{{_last_button_payload}}Payload of the last button the customer tapped (the dynamic value, e.g. a custom payload)approve_REQ123
{{_last_button_text}}Visible label of the last button tappedApprove
{{_last_row_payload}}Payload of the last list row selectedorder_42
{{_last_row_text}}Visible title of the last list row selectedOrder #42
{{_last_template_button_clicked}}Payload of the last template quick-reply button tappedconfirm_order
Extracted variables

A Button Click trigger can extract part of a payload into a variable you name (via Extract to Variable). For example, payload approve_REQ123 with pattern approve_ saved to approval_id makes {{approval_id}} = REQ123 available throughout the flow. Your extracted variables also appear in the Expression Builder's variable list.


Node names and data flow

Every node in your flow has a node name — this is how the system organizes data and how you reference a node's output in later nodes. Understanding node names is key to building flows where data moves from one step to the next.

Default node names

When you add a node to the canvas, it gets an automatic name based on its type and a sequential number:

Node typeDefault name examples
Triggertrigger_1
Messagemessage_1, message_2, message_3
Interactive Messageinteractive_message_1, interactive_message_2
Questionquestion_1, question_2
Conditioncondition_1, condition_2
Routerrouter_1, router_2
HTTP Callhttp_call_1, http_call_2
Scriptscript_1, script_2
Lead Managementlead_management_1, lead_management_2
Template Messagetemplate_message_1, template_message_2
Media Messagemedia_message_1, media_message_2
SPMinteractive_spm_1
MPMinteractive_mpm_1
WhatsApp Flowwhatsapp_flow_1
Endend_1, end_2

Renaming a node

You can rename any node to something more descriptive by editing the Node Name field in the node's configuration panel.

📸
Screenshot: Node Name input field showing name, variables hint, and reference count
node-name-input.png
1. Click on any node in the canvas to open its configuration panel
2. Find the Node Name field at the top of the config
3. Capture the field showing a custom name like "fetch_customer" with the variables hint below
Save to: static/img/screenshots/chatbot-flows/variables/node-name-input.png

The Node Name field shows a helpful hint: Variables: {{node_name.variable}} — this tells you how to reference this node's output in other nodes.

Naming rules:

  • Only letters, numbers, and underscores allowed
  • Cannot start with a number
  • Maximum 50 characters
  • Must be unique across the flow

Auto-refactoring on rename

If you rename a node that is already referenced by other nodes, the system shows a confirmation dialog listing all the places where the old name is used. If you confirm, it automatically updates all references throughout the flow.

For example, if you rename http_call_1 to fetch_order and 3 other nodes use {{http_call_1.status}}, the system will update them all to {{fetch_order.status}}.

📸
Screenshot: Node name refactor dialog showing affected references
node-name-refactor-dialog.png
1. Rename a node that is referenced by other nodes
2. Capture the confirmation dialog showing the list of affected references
Save to: static/img/screenshots/chatbot-flows/variables/node-name-refactor-dialog.png
warning

If a node name is used in other nodes (shown as "Used in X place(s)" beneath the name field), renaming it will update all those references. Make sure the new name is correct before confirming.


How data flows between nodes

When a node runs, its output is saved to the session using the node's name as a prefix. This means you can access any previous node's output by combining the node name with the variable name using dot notation.

The pattern: {{node_name.variable}}

Here's how each node type saves and exposes its data:

Question node → Variable

A Question node saves the customer's answer to a custom variable name that you specify.

SettingWhat it does
Save to variableThe variable name where the answer is stored

If you set "Save to variable" to user_email, the customer's answer is saved as {{user_email}}.

Example flow:

Question: "What's your email?"
└── Save to variable: user_email

Message: "Thanks! We'll send updates to {{user_email}}"

HTTP Call node → Response data

An HTTP Call node saves the entire response using the node's name as a prefix. You access specific fields using dot notation.

If the node is named http_call_1 and the response is:

{
"status": 200,
"result": {
"order_id": "ORD-123",
"tracking_url": "https://track.example.com/123"
}
}

You access the data as:

VariableValue
{{http_call_1.status}}200
{{http_call_1.result.order_id}}ORD-123
{{http_call_1.result.tracking_url}}https://track.example.com/123
Rename for clarity

Instead of using {{http_call_1.result.order_id}}, rename the node to something meaningful like fetch_order. Then you can write {{fetch_order.result.order_id}} — much easier to read!

Script node → Output variables

A Script node maps input variables from the session into the script, and output variables from the script back to the session. Outputs are saved with the node's name as a prefix.

If the node is named script_1 and the script returns:

return { finalPrice: 2950, taxAmount: 450 };

You access the output as:

VariableValue
{{script_1.finalPrice}}2950
{{script_1.taxAmount}}450

Template Message → Parameter mapping

A Template Message node maps variables to template parameters. Each template parameter (like {{1}}, {{2}}) is mapped to a variable.

Template parameterMapped to
Header {{1}}{{customer_name}}
Body {{1}}{{order_total}}
Body {{2}}{{delivery_date}}
Button URL {{1}}{{tracking_url}}

Trigger node → Trigger data

The trigger node's data is available using the trigger's node name as a prefix. Each trigger type provides different variables — see Trigger Blocks for the complete list per trigger type.

WhatsApp Flow node → Form response data

A WhatsApp Flow node sends an interactive form and waits for the customer to submit it. When using the Data Exchange flow action, the submitted form data is mapped to session variables through the Response Mapping section.

If you map the form fields like this:

Form fieldSession variable
full_namecustomer_name
emailcustomer_email
preferred_dateappointment_date

You access the data as:

VariableValue
{{customer_name}}Rahul Sharma
{{customer_email}}rahul@example.com
{{appointment_date}}2025-02-20

Interactive Buttons / List Menu → Customer selection

When a customer taps a button or selects a list item, the flow continues along the connected path for that specific button/row. The button or list item ID is also saved and can be referenced in subsequent nodes.

Lead Management (Get Details) → Contact data

The Get Details action fetches contact information and saves it with a prefix (default: lead_).

VariableValue
{{lead_name}}Contact's name
{{lead_email}}Contact's email
{{lead_companyName}}Contact's company

Nodes that wait for customer input

Some nodes pause the flow and wait for the customer to respond before continuing. Understanding this is important because the flow doesn't move to the next node until the customer takes action — and only then do the response variables become available.

Which nodes wait?

NodeWhat it waits forWhat gets saved
QuestionCustomer types a replyAnswer saved to the variable you specified
Interactive ButtonsCustomer taps a buttonFlow continues along the button's connected path
List MenuCustomer selects a list itemFlow continues along the row's connected path
WhatsApp FlowCustomer fills and submits the formForm data saved to session variables via response mapping

How waiting works

   ┌────────────────────────┐
│ WhatsApp Flow node │
│ "Fill booking form" │
└────────────┬───────────┘

Sends form to
customer

⏳ FLOW PAUSES ⏳
Waiting for the
customer to submit

Customer submits
the form

Response variables
become available


┌────────────────────────┐
│ Next node can now │
│ use the form data │
│ {{customer_name}} │
│ {{appointment_date}} │
└────────────────────────┘
  1. The node sends the message/form to the customer
  2. The flow pauses — no further nodes execute
  3. The customer takes action (types a reply, taps a button, or submits a form)
  4. The response is saved as variables in the session
  5. The flow continues to the next connected node
  6. The next node (and all subsequent nodes) can now use those variables

Using waiting node responses in the Expression Builder

After a waiting node saves its response, the variables become available in the Expression Builder for all subsequent nodes.

📸
Screenshot: Expression Builder showing variables from a previous WhatsApp Flow node available for selection in the Variables tab
waiting-node-response-in-builder.png
1. Add a WhatsApp Flow node followed by a Message node
2. Configure the WhatsApp Flow with response mapping (e.g., full_name → customer_name)
3. Click on the Message node and open the Expression Builder on the message text field
4. Go to the Variables tab and show the mapped variables from the WhatsApp Flow appearing in the list
5. Capture the Expression Builder showing the available variables
Save to: static/img/screenshots/chatbot-flows/variables/waiting-node-response-in-builder.png

To use a waiting node's response in the next node:

  1. Add your waiting node (e.g., WhatsApp Flow) and configure it
  2. Add the next node (e.g., a Message or Condition node) and connect it
  3. In the next node, click the code icon (</>) on any text field to open the Expression Builder
  4. Go to the Variables tab — you'll see the variables from the waiting node listed under Scenario Variables
  5. Click on a variable to insert it (e.g., {{customer_name}})

Alternatively, go to the Response tab to browse the full response structure from any previous node and click the specific field you want.

Complete example: WhatsApp Flow → Confirmation message

Here's a complete example showing how a WhatsApp Flow form response flows into a confirmation message:

[WhatsApp Flow: "Booking Form"] → booking_form
Flow action: Data Exchange
Response mapping:
full_name → customer_name
email → customer_email
preferred_date → booking_date
service_type → service

⏳ Waits for customer to submit the form...

Customer fills in:
full_name: "Rahul Sharma"
email: "rahul@example.com"
preferred_date: "2025-02-20"
service_type: "Consultation"

Session variables now available:
{{customer_name}} = "Rahul Sharma"
{{customer_email}} = "rahul@example.com"
{{booking_date}} = "2025-02-20"
{{service}} = "Consultation"



[Message: Confirmation]
"Thanks {{customer_name}}! Your {{service}} is booked
for {{booking_date}}. We'll send details to
{{customer_email}}."

Customer sees:
"Thanks Rahul Sharma! Your Consultation is booked
for 2025-02-20. We'll send details to
rahul@example.com."
tip

The same pattern works for Question nodes — the flow waits for the customer to type a reply, saves it to a variable, and subsequent nodes can use that variable via the Expression Builder.

Complete data flow example

Here's a 4-node flow that shows how data moves from node to node:

[Trigger: keyword] → trigger_1
Customer sends "order"
System variable: {{customer_phone}} = "+919876543210"



[Question: "What's your order number?"] → question_1
Customer replies: "ORD-78456"
Saved as: {{order_number}} = "ORD-78456"



[HTTP Call: GET /api/orders/{{order_number}}] → fetch_order
Response saved as:
{{fetch_order.status}} = "shipped"
{{fetch_order.tracking_url}} = "https://track.example.com/78456"
{{fetch_order.estimated_delivery}} = "14 Feb 2025"



[Message]
"Your order {{order_number}} is {{fetch_order.status}}.
Track it here: {{fetch_order.tracking_url}}
Expected delivery: {{fetch_order.estimated_delivery}}"

Expression Builder

The Expression Builder is a visual tool that helps you insert variables, build conditions, and write expressions without typing everything manually. It opens as a panel when you click the code icon (</>) on any text field that supports variables.

📸
Screenshot: Expression Builder panel showing the expression editor, tabs, and variable sections
expression-builder-panel.png
1. Open any message node or condition field
2. Click the code icon (</>) on the right side of the text field
3. Capture the full Expression Builder panel showing the expression area and tabs
Save to: static/img/screenshots/chatbot-flows/variables/expression-builder-panel.png

How to use it

  1. Click the code icon on any text field (message body, condition, URL, header, etc.)
  2. The Expression Builder opens as an overlay panel
  3. Use the tabs at the bottom to browse variables, functions, and operators
  4. Click any item to insert it at the cursor position in the expression editor
  5. Click Apply to insert the expression into the original text field

Expression editor

At the top of the panel, there's a text area where you build your expression. You can type directly or click items from the tabs below to insert them.

The editor shows real-time validation — errors appear in red and warnings in yellow below the editor.

Tabs

The Expression Builder has 5 tabs:

Variables tab

Shows all available variables grouped into sections:

SectionWhat it contains
System VariablesBuilt-in variables like {{customer_name}}, {{customer_phone}}, {{initial_message}}, {{whatsapp_message_id}}
Scenario VariablesVariables created by your flow's nodes — Question answers, HTTP Call response mappings, etc.

Click any variable chip to insert it at the cursor position in the expression editor.

Response tab

Shows the output of each node in your flow as a browsable tree. This is where you map data from a previous node's response to the current node.

📸
Screenshot: Expression Builder Response tab showing node responses as a tree
expression-builder-response-tab.png
1. Open the Expression Builder on any text field
2. Click the Response tab
3. Capture the tree view showing node names with expandable response data
Save to: static/img/screenshots/chatbot-flows/variables/expression-builder-response-tab.png

How it works:

  1. Each node in your flow is listed by its node name (e.g., http_call_1, question_1)
  2. Click the + icon next to a node to add a sample response (paste a JSON example of what the node returns)
  3. The system parses the JSON and shows all fields as a tree
  4. Click any leaf field to insert it as {{node_name.field}} in your expression

Adding a sample response:

  1. Click the + or edit icon next to any node
  2. Paste a sample JSON response (supports relaxed format — single quotes and unquoted keys work)
  3. Click Format JSON to validate and pretty-print
  4. Click Save
  5. The tree view now shows all available fields from that node
tip

For HTTP Call nodes, paste an example of the API response. For Script nodes, paste an example of the return object. This makes it easy to pick the right variable path without memorizing it.

Functions tab

Provides built-in functions you can use in expressions:

CategoryFunctionsExample
Mathsum, avg, min, max, round, floor, ceil, abs{{sum({{price}}, {{tax}})}}
Stringconcat, toUpperCase, toLowerCase, trim, length{{toUpperCase({{city}})}}
Conditionalif, ifEmpty, coalesce{{if({{age}} >= 18, 'Adult', 'Minor')}}

Each function shows its syntax, description, and an example. Toggle between compact view (chips only) and detailed view (with descriptions) using the list icon.

Operators tab

Provides operators for building conditions:

CategoryOperators
Arithmetic+ (add), - (subtract), * (multiply), / (divide), % (modulo)
Comparison== (equals), != (not equals), >, <, >=, <=
Logical&& (AND), || (OR), ! (NOT)

Example: {{{{order_total}} * 1.18}} calculates the total with 18% tax.

Text tab

Provides keywords for use in comparisons:

KeywordUsage
true / falseBoolean comparisons
nullCheck for empty values

Syntax guide

The Expression Builder includes a syntax guide at the top of the editor. Click the help icon for detailed examples covering:

  • Simple variables: {{customer_name}}
  • Nested variables: {{fetch_order.result.tracking_url}}
  • Arithmetic: {{{{price}} + 100}}, {{{{price}} * 1.18}}
  • Comparisons: {{{{age}} >= 18}}, {{{{status}} === 'active'}}
  • Functions: {{sum(100, 20)}}, {{toUpperCase({{name}})}}
  • Logical operations: {{{{age}} >= 18 && {{status}} === 'active'}}

Using variables in messages

You can insert variables in any message node. Just type {{variable_name}} where you want the value to appear, or use the Expression Builder to insert them.

Example message:

Hi {{customer_name}}, your order {{order_number}} is {{fetch_order.status}}. Expected delivery: {{fetch_order.estimated_delivery}}.

What the customer sees:

Hi Rahul, your order ORD-78456 is Shipped. Expected delivery: 14 Feb 2025.

tip

Variables work in message body text, headers, footers, button URLs, HTTP Call URLs, HTTP Call request bodies, script input variables, and template parameters — basically everywhere you type text.

Using variables in conditions

Variables are essential in Condition and Router nodes for making decisions.

Example condition: "Is the order total greater than 5000?"

  • Variable: {{order_total}}
  • Operator: greater than
  • Value: 5000

Comparison operators

When building conditions in Router nodes, you can use these operators:

OperatorWhat it checksExample
equalsExact match{{status}} equals "active"
not equalsDoes not match{{status}} not equals "cancelled"
containsText includes value (case-insensitive){{message}} contains "help"
not containsText does not include value{{message}} not contains "cancel"
starts withText begins with value{{phone}} starts with "+91"
ends withText ends with value{{email}} ends with "@gmail.com"
greater thanNumber is larger{{total}} greater than 1000
less thanNumber is smaller{{age}} less than 18
greater or equalNumber is equal or larger{{score}} greater or equal 80
less or equalNumber is equal or smaller{{quantity}} less or equal 100
is emptyVariable has no value{{email}} is empty
is not emptyVariable has a value{{phone}} is not empty

Logical operators

In Router nodes, you can combine multiple rules using:

OperatorMeaningExample
ANDAll rules must be trueCity is "Mumbai" AND Budget > 50000
ORAny rule can be trueStatus is "VIP" OR Purchases > 10

Variable naming rules

RuleDetails
Allowed charactersLetters, numbers, underscores
Case sensitive{{Name}} and {{name}} are different variables
No spacesUse underscores: {{customer_name}} not {{customer name}}
Descriptive namesUse meaningful names like {{order_total}} instead of {{x}}

Variable scope

Variables are scoped to a single flow execution (one conversation). They are not shared between different customers or different flow runs.

What's sharedWhat's not shared
Variables within one flow runVariables between different customers
Variables across all nodes in the flowVariables between separate flow runs
Variables from triggers to endVariables from one flow to another flow

What happens when a variable is empty?

If you use a variable that hasn't been set yet, it appears as an empty string in messages. For critical variables, use a Condition node to check if the variable has a value before using it:

  1. Add a Condition node
  2. Check: {{customer_email}} is not empty
  3. TRUE path → Continue with the email
  4. FALSE path → Ask for the email

Common patterns

PatternHow it works
Collect then useQuestion → saves {{name}} → Message uses {{name}}
Fetch then routeHTTP Call (fetch_order) → Condition checks {{fetch_order.status}}
Collect then sendQuestion → saves {{budget}} → HTTP Call sends {{budget}} to CRM
Fetch then displayGet Details → saves {{lead_email}} → Message shows {{lead_email}}
Calculate then showScript (calc_price) → Message shows {{calc_price.final_total}}
Trigger then personalizeAd Click trigger (trigger_1) → Message uses {{trigger_1.ad.headline}}
Chain node outputsHTTP Call (get_customer) → Script uses {{get_customer.result.id}} → Message uses {{script_1.discount}}