Skip to content

Product marketing (badges & compare-at)

Catalog variants, price quotes, and cart/checkout-preview lines can carry an additive marketing object — badges and a “was/now” compare-at price you can render directly on your own storefront. It is purely presentational: nothing in it ever affects what you pay Linra, your commission, VAT, or settlement. Treat it the same way you’d treat any other display hint from a supplier feed.

{
"id": "5b2e...",
"sku": "CREED-AVENTUS-100",
"price": 376.00,
"marketing": {
"currentPrice": 100.00,
"compareAtPrice": 120.00,
"discountPercent": 16.67,
"badges": ["LIMITED", "BEST_SELLER"],
"currentPriceDisplay": 26.60,
"compareAtPriceDisplay": 31.91
}
}

If your account doesn’t have the marketing feature enabled, the marketing key is not present at all on any response — never present with null/empty fields. Don’t write code that assumes the key always exists; check for its presence before reading anything under it. (If you’d like it enabled, ask your account contact.)

An internal catalog browse (this same schema is shared with our own admin tooling) also never carries the block — it only ever appears on a genuine partner-authenticated request.

compareAtPrice is populated only when there is a genuine reason to show a strike-through — almost always a real, recorded price drop: the catalog price for this variant was genuinely higher at some point in the past than it is right now. If the price has never changed, or the most recent change was an increase, compareAtPrice and discountPercent are both null — we never fabricate or hold onto a stale “was” price just to keep a promotion-looking badge on screen. A strike-through that was showing yesterday can legitimately disappear today if nothing about the price history changed except the passage of time relative to a more recent, higher recorded price — this is expected behavior, not a bug to report.

currentPrice here is the catalog’s own resolved price for the variant — it is shown for context next to compareAtPrice and is not necessarily identical to the partner-specific price shown elsewhere in the same response (that one already reflects any commercial terms specific to your account). Treat the two as a self-contained “was/now” pair for display, separate from what you’re actually charged.

discountPercent is a plain ratio — it has no currency and no *Display sibling.

Badge Meaning
LIMITED Stock is low (the same 3-state availability you see elsewhere on this variant).
BACK_IN_STOCK Recently came back into stock after being unavailable.
NEW_ARRIVAL Recently added to the catalog.
BEST_SELLER Currently a top-selling variant, fleet-wide, over a rolling recent window.
SAMPLE_AVAILABLE This is a sellable sample size.

badges is always an array — empty when nothing currently applies, never null. A variant can carry more than one badge at once (e.g. a new arrival that’s also a sample size). Treat unknown badge codes gracefully (render them generically or ignore them) — new codes may be added over time without a breaking-change bump.

currentPriceDisplay/compareAtPriceDisplay follow the same additive display-currency pattern as every other money field in the API (see Environments for the X-Partner-Currency header) — populated only when you’ve requested a supported non-SAR display currency, and always alongside the canonical SAR figures, never replacing them.

The marketing object can appear on:

  • GET /api/v1/scent/catalog/variants and GET /api/v1/scent/catalog/variants/{id} (per variant)
  • GET /api/v1/scent/catalog/scents/{id}/quote (per variant on the quote)
  • GET /api/v1/scent/cart and every cart-mutating call that returns a cart (per line)
  • GET /api/v1/scent/cart/checkout-preview (per line)

Every one of these reads the SAME underlying derivation for a given variant at a given moment — you won’t see the catalog and the cart independently disagree about whether a compare-at price applies.