Skip to content

Cheatsheet

TL;DR: Day-to-day commands, objects, filters, and syntax, in a quick-lookup format.

CommandDoes
shopify theme initScaffolds a new theme from Skeleton Theme
shopify theme dev --store <store>.myshopify.comLocal preview with hot reload (Chrome only)
shopify theme checkLints Liquid/JSON against Theme Check rules
shopify theme pushPushes local files to a theme on the store
shopify theme push --unpublishedPushes to a new, unpublished theme
shopify theme pullPulls a store’s theme files locally
shopify theme packageBuilds a submission-ready zip, respecting .shopifyignore
shopify theme publishPublishes a theme live
shopify theme listLists themes on the connected store
shopify theme openOpens the theme in the browser editor
shopify theme shareUploads and returns a preview link (unpublished theme)
CommandDoes
shopify theme init (select AI agent support)Scaffolds AGENTS.md + CLAUDE.md/.github/copilot-instructions.md as symlinks to it
node scripts/generate-ai-rules.mjsCreates those same symlinks by hand, for a repo not scaffolded with AI agent support
{{ product.title }}
{{ product.price | money }}
{{ product.selected_or_first_available_variant }}
{{ collection.products.size }}
{{ cart.item_count }}
{{ cart.total_price | money }}
{{ section.settings.heading }}
{{ block.settings.text }}
{{ settings.color_primary }}
{{ routes.root_url }}
{{ 'general.search.placeholder' | t }}
{{ request.locale.iso_code }}
{{ localization.country.name }}

Full detail: Liquid Global Objects Reference.

FilterExample
money{{ product.price | money }}
image_url{{ image | image_url: width: 800 }}
t (translate){{ 'cart.empty' | t }}
default{{ value | default: 'fallback' }}
escape{{ user_input | escape }}
handleize{{ 'My Title' | handleize }}my-title
where{{ products | where: 'available', true }}
first / last{{ collection.products | first }}
{%- if condition -%} ... {%- endif -%} {# strips surrounding whitespace #}
{{- value -}} {# strips whitespace around output #}
{
"name": "t:names.testimonials",
"settings": [
{ "type": "text", "id": "heading", "label": "t:settings.heading" }
],
"blocks": [
{
"type": "quote",
"name": "t:names.quote",
"settings": [
{ "type": "richtext", "id": "quote", "label": "t:settings.quote_text" }
]
}
],
"presets": [
{ "name": "t:names.testimonials" }
]
}

Locale keys are flat, and the whole theme shares them. Group them by purpose, using prefixes like names.*, settings.*, options.*, and categories.*. Don’t nest them per section, like t:sections.testimonials.settings.heading.label. See the Complete Worked Example for the full picture.

{ "blocks": [{ "type": "@theme" }, { "type": "@app" }] }

{% stylesheet %} / {% javascript %} skeleton

Section titled “{% stylesheet %} / {% javascript %} skeleton”
{% stylesheet %}
.my-component { display: grid; gap: var(--space-md); }
{% endstylesheet %}
{% javascript %}
class MyComponent extends HTMLElement {
connectedCallback() { /* ... */ }
}
customElements.define('my-component', MyComponent);
{% endjavascript %}
{%- doc -%}
@param {object} product - The product to render.
@param {boolean} [show_vendor] - Defaults to false.
{%- enddoc -%}
{ "cart": { "item_count": { "one": "{{ count }} item", "other": "{{ count }} items" } } }
{{ 'cart.item_count' | t: count: cart.item_count }}
CommandDoes
git checkout -b feature/section-nameNew branch, per Branching & Commits convention
gh pr createOpens a PR (if using GitHub CLI)
CommandRuns
/figma-to-liquid <link> <name>Full plan → build → check → fix → report loop
/theme-check-fixRuns theme check, fixes every offense
/pr-prepChecks the diff, drafts a PR description

See Claude Code Custom Commands.