Metafields & Metaobjects

Metafields in Liquid: How to Display Custom Data in Shopify

By CartStack Team3 min read

Metafields in Liquid are how you turn custom store data into real storefront content. The syntax is short, but the details trip people up. This guide shows the exact code for each common metafield type.

Cover graphic for metafields in Liquid on Shopify themes
Metafields in Liquid: every type needs slightly different output.

Read metafields in Liquid

Every metafield lives under its resource, then a namespace, then a key. Merchant-created fields use the custom namespace by default. So a field called fabric on a product looks like this:

{{ product.metafields.custom.fabric.value }}

The .value part matters. Without it, you get the metafield object instead of the data. Also, remember that namespace and key are case sensitive.

First, create the field in Settings, then Custom data. Next, fill in a value on a product. Finally, add the code to a section or snippet. You can also connect a theme setting to a metafield with the dynamic source icon in the theme editor.

Display each metafield type

Each type needs slightly different output. Use this table as a cheat sheet.

Type Liquid output
Single line text {{ product.metafields.custom.fabric.value }}
Rich text {{ product.metafields.custom.care.value | metafield_tag }}
True or false {% if product.metafields.custom.is_eco.value %}
Image value | image_url | image_tag
List of text A for loop over .value

Rich text is the one that surprises people. If you print it directly, you see raw JSON. Therefore, always pass it through the metafield_tag filter.

Show images and lists from metafields in Liquid

File and list fields return objects, not plain text. So you must unwrap them first. This example renders an image and a feature list:

{% assign img = product.metafields.custom.detail_image.value %}
{% if img %}
  {{ img | image_url: width: 800 | image_tag: loading: 'lazy', alt: img.alt }}
{% endif %}

{% assign features = product.metafields.custom.features.value %}
{% if features != blank %}
  <ul>
    {% for feature in features %}
      <li>{{ feature }}</li>
    {% endfor %}
  </ul>
{% endif %}

Notice the blank checks. They stop empty wrappers from rendering. Also, image_tag builds a responsive image with width and height, which protects your layout from shifting.

Handle empty values safely

Most products will not have every field. However, your template still runs for each one. So guard every block.

{% if product.metafields.custom.care.value != blank %}
  <h2>Care</h2>
  {{ product.metafields.custom.care.value | metafield_tag }}
{% endif %}

This check hides the heading when there is nothing to show. As a result, your product pages stay clean.

Debug metafields in Liquid

When the output is empty, work through this list.

  1. Check the namespace and key spelling.
  2. Print the type with product.metafields.custom.fabric.type.
  3. Confirm the product actually has a value.
  4. Look for a missing .value.

Also, use a definition instead of a bare field. Definitions add validation, and they expose the data to the Storefront API. For the complete reference, see the Shopify Liquid documentation.

Not sure which structure to use? Read metafields vs metaobjects first. Also keep your templates lean, because Shopify Liquid performance depends on it.

FAQ about metafields in Liquid

Why is my metafield empty? Usually the key is misspelled, or the .value part is missing.

Do I need a definition? Not always. Still, definitions make editing safer and unlock the Storefront API.

Do metafields in Liquid work on collections and customers? Yes. Use collection.metafields or customer.metafields in the same way.