Liquid template bindings deep-dive

Write valid Liquid for OmniLab notifications and understand which bindings each notification type supports.

4 min read

This guide builds on the Notifications documentation and focuses on the authoring rules that matter when you want templates to survive validation and render cleanly in production.

Where Liquid can be used

Liquid can be used in these notification fields:

  • Email Subject Line
  • Email Preheader
  • Email Content
  • Email CTA Label
  • Email CTA Link
  • The Email Banner's link

How Liquid behaves in OmniLab

  • If a documented variable has no value, it renders as an empty string.
  • Undefined variables are blocked by validation before launch.
  • Invalid Liquid syntax is blocked by validation before launch.
  • Render-time errors are also surfaced by validation.
  • The selected language variant is resolved first, then Liquid is rendered into that final text.

Binding families

Binding familyWhat it containsExample variables
CommonOrganisation, sender, reply-to, header, footer, and social linksenterprise_name, sender_from_email, reply_from_email
ContactThe current participant and contact custom fieldscontact_fullname, contact_email, contact_external_id
TouchpointThe current touchpoint or activity contextcollectible_title, collectible_location
RewardReward informationreward_display_name, reward_eligible_title
CouponCoupon or voucher detailscoupon_code, coupon_name
EventActivity and booking experience detailsevent_title, event_location
BookingBooking-specific fieldsbooking_id, booking_event_id

Organisation-level custom variables are also available directly by their own key names. That means a variable such as country can be referenced as {{ country }} if it exists in your OmniLab setup.

Use contact_fullname to greet a participant

A contact's name is stored in one of two shapes, depending on how the campaign's acquisition form collects it: as contact_firstname + contact_lastname, or as a single full name. All three bindings exist, but only one is safe to greet with:

BindingResolves to
contact_fullnameThe contact's name whichever shape they carry — the single full name, or the two parts joined, or their email address as a last resort
contact_firstnameThe given name, empty for a contact acquired through a Full Name campaign
contact_lastnameThe family name, empty for a contact acquired through a Full Name campaign

Prefer contact_fullname in new templates. A greeting written as Hello {{ contact_firstname }} {{ contact_lastname }}, renders as Hello , for those contacts, and one organisation can hold both shapes at once — so the parts are only safe when you know every contact a template can reach was collected with them.

Existing templates are not rewritten for you

Switching a campaign to a single Full Name field does not update templates already written against contact_firstname. Re-author those templates against contact_fullname at the same time, or the first send after the switch greets nobody.

Availability matrix by notification type

Notification typeCommonContactTouchpointRewardCouponEventBookingExample variables
ParticipateYesYesNoNoNoNoNocontact_fullname, enterprise_name
Touchpoint UnlockedYesYesYesNoNoNoNocollectible_title, collectible_location
WinnerYesYesNoYesYesNoNoreward_display_name, coupon_code
LoserYesYesNoYesNoNoNoreward_title, reward_display_name
EligibleYesYesNoYesNoNoNoreward_eligible_title, reward_display_name
Reward RedeemedYesYesNoYesYesNoNoreward_display_name, coupon_code
Booking ConfirmationYesYesYesNoNoYesYesevent_title, booking_id
Booking CancellationYesYesYesNoNoYesYesevent_title, booking_id
Booking Confirmation ReminderYesYesYesNoNoYesYesevent_title, booking_slot_start_date

Worked examples

Winner subject line
Congratulations {{ contact_fullname }}. You won {{ reward_display_name }}
Winner email content
Hi {{ contact_fullname }},

Congratulations. You won {{ reward_display_name }}.

Your code: {{ coupon_code }}
Booking confirmation content
Hi {{ contact_fullname }},

Your booking for {{ event_title }} is confirmed.
Start time: {{ booking_slot_start_date }}
Location: {{ event_location }}
Booking ID: {{ booking_id }}
Dynamic CTA link
https://example.com/rewards/{{ reward_id }}?contact={{ contact_external_id }}

Rules that prevent validation errors

  • Keep HTML outside the {{ }} delimiters.
  • Use only letters, numbers, underscores, and dots in variable names.
  • Do not reuse a binding family on a notification type that does not support it.
  • Keep the message readable even if one variable resolves to an empty value.
  • Re-test copied templates when you move them from one notification type to another.
Correct HTML and Liquid combination
<span>{{ contact_fullname }}</span>
Incorrect HTML inside Liquid
{{ <span>contact_fullname</span> }}

Common Liquid validation messages

ProblemValidation messageWhat to change
HTML inside Liquid{{notification_type}} {{field}} contains HTML tags inside liquid template: {{example}}Move the HTML outside the Liquid delimiters
Invalid syntax{{notification_type}} {{field}} has invalid liquid template syntax: {{error}}Balance the delimiters and fix malformed expressions
Render failure{{notification_type}} {{field}} liquid template failed to render: {{error}}Simplify the template logic and keep to supported bindings
Undefined variableUndefined liquid variable '{{variable}}' used in {{notification_type}} {{field}}Replace it with a documented binding
Binding not allowed for this typeLiquid variable '{{variable}}' ({{category}} binding) cannot be used in {{notification_type}} notification {{field}}Use a binding family that the current notification type supports

Booking notification dependency that often matters

If you enable Booking Confirmation Reminder, keep Booking Cancellation active as well. OmniLab validation explicitly checks this so participants are not reminded about a booking that can later be cancelled without a matching cancellation email.

On this page