Three steps that strip leading zeros, pad a short core to 12 digits, and label UPC or EAN from that length.
Public type follows canonical length, not the stored GTIN13 flag.

Why a 12-digit UPC-A comes back typed as GTIN13

GTIN13 on a 12-digit box code usually means the row was saved with one leading zero. Strip that zero, pad the core back to 12 digits, and label it UPC. Do not trust the stored type string by itself.

Javier Marí Lobato 4 min read

Why the type says GTIN13

A 12-digit UPC-A on a shoe box and the same digits with one leading zero are the same GTIN. The barcode store keeps more than one written length for that number. A row can hold 12 digits, 13 digits with one leading zero, or 14 digits with two leading zeros. The field product_barcode_type is set from the length of the stored string. It is not set from the 12 digits printed under the bars.

If the UPC-A was saved with one leading zero, the stored string has 13 characters. The type column is then GTIN13. The model comment says that shape is typed GTIN13 and would be read as EAN if you used the column as the public label. That is why a box you counted as 12 digits can come back with an EAN-looking type. The digits did not become a different code. A zero was kept in front.

The sneaker lookup page uses the same identity rule. A UPC-A and the same number with a leading zero are one GTIN, and the lookup treats them as one code. The reverse is not true. A 13-digit EAN that starts with any digit other than 0 has no 12-digit form, so you must keep all 13 digits. If your only extra digit is a leading zero, you still have the UPC-A.

How the public label is chosen

The public label ignores product_barcode_type. It calls canonicalValue on the stored digits, then typeLabel on that result. canonicalValue strips leading zeros to make a core. If the core is empty, or it is not all digits, the original string is returned. If the core has 12 digits or fewer, it is padded on the left back to 12 digits. If the core has 13 or 14 digits, it is returned with the leading zeros already removed.

typeLabel counts those canonical digits. A length of 12 returns the label UPC. A length of 13 returns EAN. A length of 14 returns the words GTIN 14. Any other length returns GTIN. A stored GTIN13 value whose core is 12 digits therefore gets the public label UPC. The type column and the label are allowed to disagree.

There is one documented limit. An 8-digit EAN that had been padded out to 12 digits would also receive the label UPC. The same comment says the catalog has no 8-digit EAN, so shoe rows are not in that case. For sneakers, a canonical length of 12 means UPC, and a canonical length of 13 means a real 13-digit EAN.

A separate in-memory step, unifyPerSize, can rewrite the type after it picks one code per size. If the chosen canonical code has 13 digits, it sets product_barcode_type to GTIN13. If the chosen code has 12 digits, it sets GTIN12. Rows that fail the sitemap checks are dropped first. So are 14-digit codes whose first digit is 1 through 9, because those values identify a case of pairs, not one pair. The public label rule does not change. It still uses canonical length, not the rewritten column.

The check digit is also tested on the canonical form, using the GS1 modulo 10 rule. A pass only means the number is well formed. It does not mean the stored type matches the box, and it does not prove the pair is authentic. The lookup page says a match shows which product a barcode belongs to, not that the shoes are real. If you want the family names in one place, read UPC vs EAN vs GTIN. A 12-digit UPC-A is a GTIN of length 12. Putting a zero in front does not create a new item reference.

Three steps that strip leading zeros, pad a short core to 12 digits, and label UPC or EAN from that length.
Public type follows canonical length, not the stored GTIN13 flag.
Text version

Stored type versus public label A leading zero stores a UPC-A as GTIN13. Label from canonical length. Section: How the public label is chosen Step 1: Strip leading zeros. Drop padding zeros to get the core Step 2: Pad a short core. Pad a core of 12 or fewer to 12 Step 3: Label by length. Use 12 as UPC and 13 as EAN Import mappings: stored digits to canonical form: strip zeros then pad under 13; digit length to public label: 12 UPC, 13 EAN, else GTIN

What to store in your integration

In your own code, do not branch on the string GTIN13. Copy product_barcode_value, build the canonical form, and label from that length. findByValue already searches every padded form, so a 12-digit query can hit a row stored as 13 or 14 digits. lookupCandidates keeps the raw input, the core with zeros removed, and each left-padded string from the core length through 14 digits. Store the canonical value if you need one URL or one export key. canonicalValue is what the product page and the sitemap share so they stay the same code.

Before you call the lookup, the page accepts digits only, from 8 to 15 characters. Letters and spaces will not match. If the check digit fails, you misread a digit. Use the size label on the shoe box, not a carton code or a store sticker. A valid number can still be missing from the catalog. That miss is coverage, not proof that the type field is wrong.

  • Strip leading zeros before you decide UPC or EAN.
  • Treat a 12-digit core as UPC even when the stored type is GTIN13.
  • Keep a real 13-digit core, one that is not only a padded UPC-A, as EAN.
  • Run the check digit on the canonical digits, not on a chopped copy.
  • Do not copy one barcode across sizes. Each size can have its own code.
  1. Copy the returned product_barcode_value.
  2. Strip leading zeros to get the core.
  3. If the core has 12 digits or fewer, pad it to 12 and label it UPC.
  4. If the core has 13 digits, label it EAN and keep all 13.
  5. Ignore product_barcode_type when it disagrees with that length.

Frequently asked questions

Should I change the last digit because the type says EAN?

No. The check digit belongs to the canonical number. A GTIN13 type on a padded UPC-A is a storage length, not a bad final digit. Recompute the check digit only after you build the canonical form.

Is a leading-zero 13-digit string the same code as the 12-digit UPC-A?

Yes, when the extra digit is only a leading zero. A 13-digit EAN that starts with 1 through 9 has no 12-digit form. Keep all 13 digits in that case and label it EAN.

Read our guides first in Google results: add Barcodes.gg as a preferred source.