Building Merchant-Editable Sections
Every section file ends with a {% schema %} JSON block. Schema defines settings (text, images, collection pickers), blocks (repeatable sub-components), presets (add-to-page defaults), and constraints (max blocks, enabled_on templates).
Featured collection section with schema
{%- comment -%} sections/featured-collection.liquid {%- endcomment -%}
{%- liquid
assign collection = section.settings.collection
assign limit = section.settings.products_to_show
-%}
<section class="featured-collection color-{{ section.settings.color_scheme }}">
{% if section.settings.heading != blank %}
<h2>{{ section.settings.heading }}</h2>
{% endif %}
{% if collection != blank %}
<div class="grid grid--{{ section.settings.columns }}">
{% for product in collection.products limit: limit %}
{% render 'product-card', product: product %}
{% endfor %}
</div>
<a href="{{ collection.url }}" class="btn">View all</a>
{% else %}
<p>Select a collection in the theme editor.</p>
{% endif %}
</section>
{% schema %}
{
"name": "Featured collection",
"tag": "section",
"class": "section-featured-collection",
"settings": [
{ "type": "text", "id": "heading", "label": "Heading", "default": "Featured courses" },
{ "type": "collection", "id": "collection", "label": "Collection" },
{ "type": "range", "id": "products_to_show", "min": 2, "max": 12, "step": 1, "default": 4, "label": "Products to show" },
{ "type": "select", "id": "columns", "label": "Columns", "options": [
{ "value": "2", "label": "2" },
{ "value": "3", "label": "3" },
{ "value": "4", "label": "4" }
], "default": "4" },
{ "type": "color_scheme", "id": "color_scheme", "label": "Color scheme", "default": "scheme-1" }
],
"presets": [{ "name": "Featured collection" }]
}
{% endschema %}Blocks Inside Sections
Blocks let merchants add repeatable content units (slides, testimonials, feature rows) within one section. Loop section.blocks and use block.shopify_attributes for editor drag-and-drop.
Block type switching
{% for block in section.blocks %}
<div class="slide" {{ block.shopify_attributes }}>
{% case block.type %}
{% when 'heading' %}
<h3>{{ block.settings.text }}</h3>
{% when 'text' %}
<div class="rte">{{ block.settings.body }}</div>
{% when 'button' %}
<a href="{{ block.settings.link }}" class="btn">{{ block.settings.label }}</a>
{% endcase %}
</div>
{% endfor %}Note: Use section.settings for section-level config and block.settings for per-block config. Access via section.id for unique HTML IDs in JavaScript.