Blog
How to track expiry dates in Shopify (2026)
24 September 2026 · Datima.ai
Shopify knows how many units of each variant you have at each location, to the unit, in real time. It does not know when any of them expire. There is no expiry field on a product, a variant or an inventory level, and there never has been. If you sell food, drink, supplements, cosmetics, pet food or anything else with a date on it, the date lives somewhere else — and where you put it decides whether your numbers stay true.
This is a practical guide to the three ways merchants track expiry dates on Shopify today, what separates the ones that work from the ones that quietly rot, and how to set the working one up in an afternoon.
Where Shopify keeps quantities, and where it keeps nothing
Inventory in Shopify is a number per variant per location. Sales, refunds and adjustments move that number, and everything downstream — low-stock reports, availability on the storefront — reads it. A date has nowhere to sit in that model. You can attach one with a metafield, but a metafield is a label: it does not change when you sell three units, and it cannot say that the 40 units on the shelf are really 16 from March and 24 from June with different dates. Anything about expiry has to be built beside inventory and kept in step with it.
The three ways merchants do it
1. A spreadsheet
Everyone starts here, and it works for a month. Then a second delivery of the same product arrives with a different date, and one SKU becomes two rows. Then a refund comes back and nobody knows which row it belongs to. The spreadsheet never sees a sale, so someone reconciles it by hand every week — and every week it is a little more fiction. The failure is not discipline; it is that expiry data decays with every order, and only a system that sees the orders can keep it honest.
2. A product metafield or a tag
Better than nothing: a date on the product that your theme can show. But it is one date per product, so it is wrong the moment a second delivery lands, and it still does not move when you sell. Use metafields as an output — the earliest date, written by whatever tracks the batches — not as the record itself.
3. Batch (lot) tracking
One row per delivery: quantity, expiry date, and if you use them a lot code and a bin. Sales come off the batch that expires first (the rule warehouses call FEFO), refunds go back to the batch they came from, and the product's “expiry date” is simply the earliest batch that still has stock. This is the only approach that survives a busy week without anyone touching a spreadsheet, and it is what an expiry app should be doing under the hood.
What to look for in an expiry app
- Batches, not products. If the app stores one date per product, it has already lost.
- FEFO on every sale, refunds included. The numbers should stay true without you.
- Windows in money. “What expires within 7, 30 and 90 days, and what is it worth” is the question you actually ask; the answer should be one screen.
- An import that starts from your catalog. Typing 200 products into a form is how setups die. The template should come pre-filled.
- The date where the customer sees it. A best-before date on the product page, without a developer.
- Alerts that reach you. An email when something is about to expire, on a day you choose.
- Locations. A batch sits somewhere; a sale should consume it where it shipped from.
Setting it up in an afternoon, with Datima
Datima is our app for exactly this. It is free, with no limit on products, and it runs in English, German, French and Spanish. The setup:
- Install it from the Shopify App Store. Your catalog syncs on the first open — products, images, locations.
- Download the CSV template. It already lists your products and variants; you fill two columns,
expiry_dateandquantity, for whatever is on the shelf. Rows you do not know yet stay empty — they are skipped, not errors. - Import it. Every row is validated first and nothing is written until you confirm. Rows that fail come back as a file in the same shape, so you fix the values and upload again.
- From now on, record deliveries as batches. Thirty seconds each: date, quantity, optionally a lot code and bin. Or select twenty products and give them all the same date in one go.
- Read the dashboard. Expired, within 7, within 30, within 90 days — each with its value at your price. A weekly digest lands in your inbox on Monday morning, and you can change the day or switch it off.
- Optional: show the date on your product pages. Add the Best-before block in your theme editor; it reads the earliest date of the selected variant and says “use soon” when it is close. The same date is on a metafield, so Shopify Flow or another app can read it.
The getting-started guide walks through each step with screenshots, and the three-minute video shows the whole loop on a real store.
Three questions we get
We have several locations. A batch carries its location, and a sale consumes the earliest batch at the location that fulfilled it — stock in the other warehouse is never touched.
What happens on a refund? The units go back onto the batch they were taken from. Nothing is invented; if a sale ever outran what was recorded, the app shows it as unmatched instead of guessing.
Some of our stock has already expired. Import it anyway. It lands under “Expired” with its value, which is often the number that gets a first stocktake approved.
If you run perishable stock on Shopify, this is the afternoon that ends the spreadsheet. Install Datima — free, no product limit — and reply to any of our emails if something in your setup does not fit the steps above.