Shopify field mapping
Shopify variant price to price
variant.price
price
The Shopify variant price is the amount a customer pays in the store currency, and the feed price has to match what the shopper will see on the landing page. What makes this non-trivial is tax treatment, currency formatting, and every discount mechanism that never touches this field.
The Shopify side
- API field
- variant.price
- Called
- Price
- Found at
- Product → Variants → edit variant → Pricing → Price
- Feeds
- price
Before and after
Real values on the left as Shopify stores them, on the right as a channel needs them.
| In Shopify | In the feed | Note |
|---|---|---|
| 49.00 (GBP store) | 49.00 GBP | Amount and ISO code, no symbol. |
| 1234.50 | 1234.50 GBP | No thousands separator. A comma here is read as a decimal point by some parsers. |
| 49.00 (OpenAI feed) | "49.00 GBP" | One string containing amount and currency for that channel. |
| 49.00 with DE market price 56.00 | 56.00 EUR in the German feed | The market price, not the converted store price. |
| 49.00 with a 10% automatic discount | 49.00 GBP | The discount is applied at checkout and is invisible here, which is why the page and the feed disagree. |
The transformation, step by step
-
Read the price from the variant
Price is per variant, so a large costing more than a small is normal and a product-level feed cannot express it. This is one of the clearest reasons a feed has to be variant level.
-
Format the amount consistently
Two decimal places, a full stop as the decimal separator, no thousands separator and no currency symbol in the number. A comma as a decimal separator is read as a thousands separator by some parsers, which turns 1.234,00 into a very different price.
-
Attach the currency the way the channel expects
Most channels take the amount with an ISO code alongside, as "49.00 GBP". OpenAI wants exactly one string containing both. Either way the currency must be the market's, not the store default.
-
Decide the tax treatment per market
EU markets expect the price to include VAT. The US expects tax excluded and handled separately. Shopify stores one number, so which one it is depends on the store's configuration, and the feed for each market has to state the right thing.
-
Check it against the landing page
Google compares the feed price with the price it finds on your product page. A correct value that the page contradicts, because of a discount app or a market-specific price, is a disapproval even though the feed is internally consistent.
What goes wrong
Checkout discounts never reach the feed
Automatic discounts, cart price rules, customer-specific pricing and app-driven promotions all apply after the product data. The feed shows the undiscounted price, the landing page may show less, and the channel treats the difference as a feed error.
Tax treatment is a market decision, not a field
Shopify holds one number whose meaning depends on store configuration. Sending a tax-excluded price into an EU feed understates every price, and the mismatch is with the page rather than within the feed, so it is only caught by the channel.
Currency conversion is not a market price
Converting the store price at today's rate produces a number that does not match what the storefront charges, because Shopify Markets applies its own rounding and price adjustments. The market price has to be read, not calculated.
A zero price is not a free product
Zero usually means a placeholder, a configurable product or a data error. Channels reject a zero price, which is the right outcome, but it needs finding in the catalogue rather than in the error report.
How feedlab maps it
feedlab formats price per channel from one internal amount and currency, reads market-specific prices rather than converting the store price, and applies the tax convention chosen for each market. Zero and missing prices are surfaced in the preview, since they are always data problems rather than values.
Frequently asked questions
Should the feed price include tax?
It depends on the market. EU markets expect VAT included; the US expects tax excluded and handled separately. Shopify stores one number, so the treatment has to be decided per feed.
Why does the channel say my price does not match my page?
Most often a discount that applies at checkout rather than in the product data, or a market-specific price that the feed did not use. Both make the page and the feed disagree while the feed is internally correct.
How should the price be formatted?
Two decimal places, a full stop as the decimal separator, no thousands separator, and the ISO currency code alongside the amount. OpenAI wants both in a single string.
Can I convert my store price for another market?
No. Shopify Markets applies its own rounding and adjustments, so the converted figure will not match what the storefront charges. Read the market price instead.
Errors this mapping causes
Attributes involved
- price The price attribute is the item's full price before any discount, submitted as a number followed by an ISO 4217 currency code. It must match what a shopper sees on the landing page in that market, including whether tax is included, which is why multi-market Shopify stores so often trip the price mismatch disapproval.
- sale_price The sale_price attribute is the temporarily reduced price of an item, submitted alongside the full price so a channel can show the reduction rather than simply a lower number. On Shopify the reliable source is the variant's compare-at price relationship, and discounts applied by code or automatic rule are not visible in the product record at all.
Related concepts
Primary sources
Channel specifications change. These are the official documents this page is based on.