Phase 5:
App Data Simulation

Resilient rendering of app-like metafields across cards & PDP

WinSport Theme · app_data Namespace · Defensive Coding

Why App Data?

2
Touchpoints
3
Metafield Keys
0
Errors If Removed

Shopify apps (reviews, badges, subscriptions) store data as metafields in their own namespaces. Themes must render this data across multiple surfaces — and survive gracefully when the app is uninstalled and its data disappears.

custom.*

Phase 4 — Store-owned

Metafields defined by the store (care_instructions, difficulty_rating, is_new_arrival). Controlled by the merchant.

app_data.*

Phase 5 — App-owned

Metafields that simulate an external app (badge text, certifications JSON). May disappear if app is uninstalled.

3 Metafield Keys

boolean

badge_enabled

Controls whether the badge is visible on product cards in collections

Surface: Collection cards
single_line_text

badge_text

Custom badge text — “Best Seller”, “Pro Pick”, “Award Winner”

Surface: Collection cards
Best Seller
json

extra_info

Structured object with warranty, origin, and certifications array

Surface: PDP
Warranty 2 years
Certifications CEISO 9001

Collection Badge

Card with App-Data Badge
Collection page with Best Seller badge
  • Badge reads app_data.badge_enabled — must be true
  • Text from app_data.badge_text — must be non-blank
  • Positioned top-left overlay, separate from Shopify’s Sale/Sold Out badges
  • Double-guard: enabled check first, then text check — either missing = no output

PDP Certifications

Collapsible Certifications Section
PDP with Product Certifications
  • Reads app_data.extra_info as JSON
  • Each key checked independently: warranty, origin, certifications[]
  • Certifications rendered as pill tags via for cert in app_info.certifications
  • Collapsible accordion matching Phase 4 design pattern

Admin Setup

Metafield Definitions
Admin metafield definitions
Product Values
Admin product metafield values

Code Highlights

{# Card badge — double guard: enabled + text #}
{%- assign app_badge_enabled = card_product.metafields.app_data.badge_enabled.value -%}
{%- if app_badge_enabled == true -%}
  {%- assign app_badge_text = card_product.metafields.app_data.badge_text.value -%}
  {%- if app_badge_text != blank -%}
    <span class="card__app-badge">{{ app_badge_text | escape }}</span>
  {%- endif -%}
{%- endif -%}

{# PDP — JSON keys checked independently #}
{%- assign app_info = product.metafields.app_data.extra_info.value -%}
{%- if app_info != blank -%}
  {%- if app_info.warranty != blank -%} … render warranty {%- endif -%}
  {%- if app_info.origin != blank -%} … render origin {%- endif -%}
  {%- if app_info.certifications != blank -%}
    {%- for cert in app_info.certifications -%}
      <span class="cert-tag">{{ cert | escape }}</span>
    {%- endfor -%}
  {%- endif -%}
{%- endif -%}

Key Takeaways

  • Separate namespaceapp_data.* vs custom.* mirrors real app architecture
  • Multi-surface rendering — same data flows to collection cards AND PDP
  • JSON metafield — structured data parsed natively by Shopify, each key accessed independently
  • Defensive at every level — namespace, key, and nested keys all checked before rendering
  • App-uninstall safe — if all app_data metafields are removed, zero output, zero errors

WinSport Theme · Phase 5 Complete · Dawn v15.4.1 · Shopify 2.0