Encode for the destination (HTML text, attributes, URLs, JSON) and guard optional data with is_valid or default.
Templates often depend on data that might be missing: an optional custom field, a query parameter that was not supplied, or a value passed into a partial under another name. The other half of safe output is encoding for the destination. A field printed in an HTML text node is not encoded the same way as that same value in a tag attribute, a CSS class, a URL, or JSON.
Most Marketpath fields (text, textarea, select, and similar) HTML-encode their default output. Printing {{ entity.title }} or {{ item.title }} in an HTML text node is usually correct. Do not pipe that default output through the escape filter — that double-encodes, and it can escape preview markup such as span tags. On the current page, output {{ entity.title }} for the heading; do not treat it as an optional plain string with the default filter, and do not wrap root entity in is_valid. Guard renamed copies such as item when a partial receives entity as an input.
The raw unencoded value is {{ field.value }}. Use .value when you need the string itself: HTML attributes, filter chains, or a partial that expects a plain string. In attributes, always use .value and escape, even on required fields, because default field output is HTML-oriented and may include preview markup that does not belong in an attribute:
Choose a filter for the destination, not one generic “safe” filter. Use escape (or html_encode, which performs the same encoding) for HTML text and attributes. Use classname for class names, url_encode for query values, and json_encode for JSON. HTML escape does not make a URL or a JSON payload correct. Prefer escape over escape_once for ordinary unencoded text.
Two field types break the usual encoding rule. An html field is trusted markup; escaping it usually defeats the field’s purpose. A code field’s default output is the raw value — treat it as unsafe and use it with extreme caution.
For missing data, prefer {% if item.is_valid %} over a bare {% if item %} when item is a documented object. Bare truthiness is mainly for checking whether an unbound input variable exists. Wrap optional sections (an image, a link, a whole block) in {% if %} so you do not render empty tags or broken markup.
Use the default filter when a fallback is intentional. It returns the fallback when the input is null, an empty string, or invalid (is_valid is false). It does not treat the boolean false as missing. For an optional custom field in HTML:
If you would rather keep the template readable, bind the field with {% var %}, test is_valid, and output the field (for a text node) or .value | escape (for an attribute). When a reusable partial expects a plain string, pass a string at the include boundary (for example title: item.title.value), not the field object.
When an input may be either a plain string or a field object, one chain resolves both: {{ input.value | default: input | default: "Fallback" | escape }}. An empty or missing field falls through to the next default because is_valid is false, and the result is a string suitable for an HTML text node or, unchanged, an attribute.
These habits keep encoding correct and keep missing data from producing errors or empty markup. See the linked examples, the default and escape filters, and the is_valid condition for more detail.
ExampleCheck if an object or value is valid with is_validCheck whether an object or value is valid (non-empty, present) with is_valid before using it.
Liquid
{%- if random_object is_valid -%}
{%- include "display_random_object" object:random_object -%}
{%- endif -%}
If field.is_valid
Liquid
{%- if field.is_valid -%}
{{-field.value-}}
{%- endif -%}
Every field and most objects have an is_valid property that can be used to check if the field or object has a valid value (non-null, non-empty, non-false, published entity, etc.). If you expect the field to be an object with an is_valid property, then this is the best way to check if it has a valid value.
If variable is_valid
Liquid
{%- if varname is_valid -%}
{{-varname-}}
{%- endif -%}
The is_valid conditional expression checks to see if a variable currently holds a valid value (non-null, non-empty, object with is_valid == true, etc.). This works for most cases, whether or not the variable is an object or a simple value
Unless variable is_valid
Liquid
{%- unless varname is_valid -%}
... do something if varname is NOT valid...
{%- endunless -%}
The unless conditional makes it easy to do something if the is_valid condition does NOT evaluate to true
is_valid conditional when used on false values
Liquid
{%- var falsevar = false -%}
{%- if falsevar is_valid -%}
false is_valid evaluates to TRUE!
{%- else -%}
this will never be output
{%- endif -%}
When using the is_valid condition on a false value, it will evaluate to true. This is by design, allowing the is_valid condition to be used to check whether or not a boolean variable has been defined
ExampleHow to use the default filterUse the default filter to output a fallback when a value is null, empty, false, or invalid. Shown for strings, numbers (e.g. query parameters), and optional display.
String default
Liquid
{%- var greeting = "" -%}
{{- greeting | default: "hello" }} world
{%- set greeting = "goodbye" -%}
{{- greeting | default: "hello" }} world
Output
hello world
goodbye world
Output a default value when the input string is null or empty.
Provide a default value for a numeric query parameter when missing or invalid. The to_int filter is used to convert the query parameter to a number if it is not already a number.
Take .value so default sees a string (or an invalid/empty field), then escape for HTML. Do not pipe a field’s default output through default as if it were a plain string, and do not use default on entity.title.
Combine default with other filters; filters are applied in the order they are listed.
ExampleOutput a field in an HTML attributeUse .value and escape when printing a field inside an HTML tag attribute. Default field output is for HTML text nodes, not attributes.
ExampleEscape HTML (escape and escape_once)Escape HTML characters for safe output inside other HTML. Use escape for full escaping; use escape_once when content may already be partially escaped to avoid double-encoding.
escape
Liquid
<p title="{{"<p>A string with HTML & other characters</p>" | escape}}">...
Output
<p title="<p>A string with HTML & other characters</p>">...
Escapes all HTML and special characters.
escape_once
Liquid
<p title="{{"<p>A string with some characters encoded & others not encoded</p>" | escape_once}}">...
Output
<p title="<p>A string with some characters encoded & others not encoded</p>">...
Escapes only characters that are not already escaped, avoiding double-encoding.