Skip to content

Product variants

Per-Shopify-variant reads, metafield administration, and bulk recalculation.

BetaAPI v2 is in public beta: endpoints, fields and behaviour can change before general availability. See the changelog

Last updated

The product-variants resource reads one Shopify variant as the Preorders > Products tab lists it and runs administrative actions on its Shopify metafields. To list variants across offers, use GET /preorders/products.

URLs use the Shopify variant id (:shopify_variant_id), a gid://shopify/ProductVariant/... gid; a numeric id also works. Escape the gid in a path.

Path prefix: /preorders/product_variants

Method Path Description
GET /preorders/product_variants/:shopify_variant_id One variant as GET /preorders/products lists it, with the offers it is in.
GET /preorders/product_variants/availability Beta. Resolve whether variants are on preorder for a buyer country. See Variant availability.

The read returns { "variant": {...}, "offers": [...] }. variant is a Products tab row: our id, shopify_variant_id, product, and offers[] with that variant’s shipping_text, max_count, quantity_limit, preorder_count and quantity_limit_reached on each offer. max_count is the variant’s own limit, the field PATCH /preorders/products writes; quantity_limit is read-only, the limit that applies (null for none), which on a batch offer is the total of the variant’s batch limits. On a batch offer, PATCH /preorders/products refuses max_count with 422; set batch_limits on the offer’s variant instead. offers holds the facts of those offers, as in GET /preorders/products, including each offer’s current_status (live, scheduled or off). A variant in no offer returns 200 with empty offers; 404 means STOQ has no row for it.

These actions compose with Shopify metafield writes. They’re the same operations the merchant admin offers behind the “Reset” / “Recalculate” buttons on the variant detail page.

Method Path Description
POST /preorders/product_variants/:shopify_variant_id/recalculate_preorder_count Recompute preorder_count from active order line items, then push to Shopify.
POST /preorders/product_variants/:shopify_variant_id/reset_preorder_count Reset the count to zero on every offer. Orders counted so far stop counting, so the next order counts from 1.
POST /preorders/product_variants/:shopify_variant_id/sync_metafields Force-resync every preorder metafield from local DB state to Shopify. Idempotent.
POST /preorders/product_variants/:shopify_variant_id/reset_metafields Clear a variant’s preorder count metafields and rebuild its shipping text and limit metafields from its live offers. Doesn’t detach from offers.
POST /preorders/product_variants/:shopify_variant_id/detach_from_all_offers Remove a variant from every preorder offer it’s attached to. Customer orders are unaffected.

Each returns the variant as the read does, { variant, offers }. detach_from_all_offers adds detached_offer_ids and failed.

  • recalculate_preorder_count — use when count has drifted from reality. Recomputes from real orders.
  • reset_preorder_count — destructive zero. Use only when you need to manually start counting from scratch.
  • sync_metafields — use after a transient Shopify outage to push DB state back into Shopify metafields.
  • reset_metafields — clears the count metafields and rebuilds shipping text and limit from the live offers. Keeps the offer attachment.
  • detach_from_all_offers — destructive; equivalent to the offer’s products/remove_variants against every offer the variant is in.

The bulk variants of the above actions submit a background job and return 202 Accepted with a job_id / status_url / variant_count. Cap is 5000 variants per submission.

Method Path Description
POST /preorders/product_variants/bulk_recalculate_preorder_counts Recompute preorder_count for many variants in one job.
POST /preorders/product_variants/bulk_reset_metafields Reset preorder metafields for many variants in one job.
POST /preorders/product_variants/bulk_sync_metafields Force-resync preorder metafields for many variants in one job.
{ "shopify_variant_ids": ["gid://shopify/ProductVariant/123456", "gid://shopify/ProductVariant/789012"] }

shopify_variant_ids are Shopify variant gids; numeric ids also work.

GET /preorders/product_variants/jobs/:job_id

Open in the API reference

Returns the standard async-job envelope. See Bulk & Async Jobs for the full polling pattern.

Was this page helpful?

Still stuck? Ask Quinn or chat with support