Shopify headless storefront guide

Purpose

This guide explains how a Shopify headless storefront should prepare a signed config payload, expose it to the Tern storefront module, and mount <tern-trade-in>.

This is the recommended integration path when the storefront can identify the shop and, optionally, the logged-in Shopify customer.

If you are not a Shopify merchant, use Non-Shopify Headless Storefront Integration Guide.

If you cannot use headless authentication at all, use Standalone Storefront Integration Guide.

Recommendation First

Use this guide when:

  1. The storefront belongs to a Shopify shop.

  2. You can generate merchant-signed bootstrap payloads on your backend.

  3. You may need anonymous or logged-in customer bootstrap.

  4. You want the recommended trust model for headless integrations.

Summary

The implementation has three steps:

  1. Get the merchant shared secret from Tern.

  2. Use that shared secret on your backend to sign the bootstrap request payload.

  3. Expose window.ternStorefrontConfig before mounting <tern-trade-in>.

Shared Secret

Before implementing the bootstrap call, obtain the merchant shared secret from the Tern admin interface for the relevant shop.

Implementation guidance:

  1. Generate or copy the shared secret from the Tern admin interface.

  2. Store the shared secret on your backend.

  3. Do not expose the shared secret in browser code.

  4. Use the shared secret only on the server when generating the HMAC signature.

Config Format

Expose window.ternStorefrontConfig with these fields:

  1. shopDomain

  2. locale

  3. proof

  4. Optional customerLogin

Browser config uses shopDomain. The storefront runtime converts that to the API field shop_domain before calling the bootstrap endpoint.

Optional customerLogin

Use customerLogin when you want to override where unauthenticated customers are redirected for login.

customerLogin supports:

  1. path: the login path on the current origin (must start with /)

  2. redirectParam: query-string key used to return from login

If omitted, storefront uses:

  1. path = /account/login

  2. redirectParam = checkout_url

Example:

Supported Bootstrap Flows

Merchant-Signed Anonymous Bootstrap

Use this when you want a signed storefront config without attaching a customer.

Merchant-Signed Logged-In Bootstrap

Use this when you want the storefront config to identify a logged-in customer.

How To Sign The Request

When using merchant_signed, your backend must sign the full canonical string shown below with HMAC-SHA256 using the merchant shared secret.

The result of that HMAC operation becomes proof.signature in window.ternStorefrontConfig.

Only these four values are part of the signature:

  1. email

  2. shop_domain

  3. id

  4. timestamp

Sign this exact canonical string:

Rules:

  1. email must be lowercased and trimmed.

  2. shop_domain must be the Shopify shop domain for the target store.

  3. id must be the logged-in customer id, or 0 when the bootstrap is anonymous.

  4. timestamp must be a Unix timestamp in seconds.

  5. The signature must be lowercase hex.

  6. Generate the signature on your backend, never in browser code.

Node.js Example: Anonymous Signing

Node.js Example: Logged-In Customer Signing

In the logged-in example:

  1. The signed string includes the normalized email and Shopify customer id.

  2. The customer object in the request must match the values used to build the signed canonical string.

  3. If these values do not match, Tern will reject the request.

For anonymous merchant-signed bootstrap, omit proof.customer entirely and sign with an empty email and id=0.

Bootstrap Response

After the storefront module initializes, it obtains a bootstrap response that includes:

  1. token

  2. locale

  3. ga_measurement_id

  4. Optional shopify_customer

Example response:

Browser Runtime And Mount

Your page must load the Tern storefront runtime before you try to mount <tern-trade-in>.

If you are using the built browser bundle, load it first:

Then define window.ternStorefrontConfig before mounting <tern-trade-in>. The storefront module uses that config to initialize the storefront session internally.

Example head

Example body

What The JavaScript Example Assumes

The JavaScript snippets in this guide are integration snippets, not complete standalone pages.

They assume:

  1. Your page already includes the Tern storefront bundle, for example https://prod.tern.eco/js/storefront/trn-nrc-umd.js.

  2. Your page already contains a mount target such as <div id="tern-storefront-root"></div>.

  3. The HMAC signature was generated on your backend before the browser set window.ternStorefrontConfig.

  4. The browser can load the Tern storefront bundle successfully.

If you paste the snippet into a page without those prerequisites, it will not work on its own.

Implementation Checklist

  1. Obtain the merchant shared secret from the Tern admin interface.

  2. Store the shared secret on your backend.

  3. Build and sign the canonical payload on the backend.

  4. Expose shopDomain, locale, and proof in window.ternStorefrontConfig before mounting the storefront.

  5. Optionally set customerLogin.path and customerLogin.redirectParam to control login redirect behavior.

  6. Load the storefront browser bundle, for example https://prod.tern.eco/js/storefront/trn-nrc-umd.js.

  7. Mount <tern-trade-in> after window.ternStorefrontConfig is defined.

  8. Let the storefront module initialize the storefront session from that config.

  9. Use the returned token from the bootstrap response as the storefront session token.

Last updated