· MicroPIM Team · Platform Migration · 20 min read
What Breaks During a Shopify Migration (And How to Prevent It)
A frank failure analysis of the most common Shopify product catalog migration errors — variant images, metafield loss, inventory reset, URL changes, and duplicate creation — with the exact cause and fix for each.
What Breaks During a Shopify Migration (And How to Prevent It)
AEO answer: The most common Shopify product migration failures are: (1) variant images assigned to wrong variants due to Shopify’s CSV row ordering requirement, (2) custom attributes and metafields silently dropped because they have no CSV column, (3) inventory levels reset to zero when catalog and inventory migration are not sequenced correctly, and (4) duplicate products created by running the import twice without deduplication. Each is preventable with a validated staging import.
Most Shopify migration write-ups describe what should happen. This one describes what actually happens — the specific failure modes that catch catalog managers off-guard, the exact mechanism behind each, and the concrete prevention step for each failure.
The honest framing: these failures are not edge cases. Variant image misassignment, custom attribute loss, and inventory reset happen in the majority of migrations where the catalog data is not prepared through a staging step first. Understanding the failure mode before it occurs is the difference between a clean cutover and a post-launch cleanup that takes longer than the migration itself.
Table of Contents
- The Five Catalog-Level Failures That Happen in Almost Every Shopify Migration
- Variant Image Mapping Failure
- Metafield and Custom Attribute Loss
- SEO Impact: Handle Changes and URL Redirects
- Inventory Reset to Zero
- Duplicate Product Creation
- The Staging Import Checklist
- How a PIM Prevents These Failures
- Frequently Asked Questions
1. The Five Catalog-Level Failures That Happen in Almost Every Shopify Migration
[E-E-A-T HOOK — Experience]: The opening claim “these failures happen in almost every migration” is strong and should be grounded in first-hand evidence. Add a note like: “Based on [N] catalog migrations supported by the MicroPIM team, [X]% involved at least one of these failure modes before a staging import step was added.” If exact data is not available, reframe as: “In our experience supporting migrations, these five failures appear consistently across platform types.” [INTERNAL LINK: → /study-cases]
[E-E-A-T HOOK — Citation needed]: The claim about SEO handle changes and Google de-indexing timeline (“within days”) should be supported by a citation. Consider linking to Google’s own documentation on how quickly 404 responses affect indexing: developers.google.com/search/docs/crawling-indexing/remove-information.
[CITE: Google Search Central — how Googlebot handles 404 responses — developers.google.com/search/docs/crawling-indexing/http-network-errors — authoritative source for the de-indexing timeline claim]
[CITE: Google’s URL removal tool documentation — developers.google.com/search/docs/crawling-indexing/remove-information — relevant to the SEO failure mode in section 4]
[E-E-A-T NOTE — Trust, balanced view]: The article frames all five failures as preventable with a staging import. Add an honest qualifier: “A staging import catches structural and mapping failures. It does not catch all failures: a supplier-side data quality problem (incorrect weight values, wrong GTINs) will survive a staging import and surface only after launch when customers or marketplace algorithms flag the bad data.”
Five failures appear consistently across Shopify migrations from every source platform. Each has a distinct mechanism and a distinct prevention step. They are named here at the start so readers can navigate directly to the one most relevant to their current situation.
Variant image misassignment — images appear on the wrong product variants; customers purchasing a red product see a blue product image. Visibility: immediate, customer-facing, high priority.
Metafield and custom attribute silent loss — custom attributes from the source system are dropped during CSV import with no error; compliance fields, technical specs, and B2B data disappear invisibly. Visibility: requires active investigation; not apparent in the product list view.
Inventory reset to zero — inventory levels are wiped or populated with stale pre-migration counts; products appear out-of-stock on launch day. Visibility: immediate operational impact; may trigger false backorder notifications.
SEO handle/URL changes without redirects — all previously indexed product URLs return 404s; organic traffic drops over 2–4 weeks as Google de-indexes the old URLs. Visibility: delayed; impact emerges in search console, not immediately at launch.
Duplicate product creation — multiple records for the same product appear in the catalog with different handles; search, navigation, and reporting are distorted. Visibility: detectable by comparing product count against source system immediately post-import.
| Failure | Visibility | Business Impact | Time to Detect | Preventable by Staging Import? |
|---|---|---|---|---|
| Variant image misassignment | Immediate (customer-facing) | High — wrong product visuals | Minutes post-launch | Yes |
| Metafield silent loss | Delayed (requires audit) | Medium–High — SEO, B2B, compliance | Hours to days | Partial (catches structural gaps; not source data errors) |
| Inventory reset to zero | Immediate (operational) | High — oversell / backorder | Minutes post-launch | Yes (if sequencing is corrected) |
| SEO URL changes without redirects | Delayed (2–4 weeks) | High — organic traffic loss | 2–4 weeks post-launch | Yes |
| Duplicate product creation | Near-immediate (count check) | Medium — catalog integrity | Immediately if count is checked | Yes |
2. Variant Image Mapping Failure: Why Variant-Specific Images End Up on Wrong Variants
Variant image misassignment is the failure mode that generates the most customer complaints post-launch. It is also one of the most preventable with a single pre-import check.
2a. Root Cause
Root cause: Shopify’s CSV assigns a variant image by reading the Variant Image URL from the same row as the variant’s option values. The URL is assigned positionally — the image on row N goes to the variant on row N. If the rows are in the wrong order, or if the image URLs appear on the wrong rows, the assignment is incorrect. Shopify does not validate that the image matches the variant’s option values. It does not cross-reference a red variant with a red image URL. It reads the row, takes the URL, and assigns it.
2b. The Common Scenario
The source platform exports variants in the order they were created or in alphabetical order. The image columns are in a different order — perhaps the order in which images were uploaded, or the order from the original product catalog. When these two orderings do not match, every image assignment after the first mismatch point is wrong.
A concrete case: size variants are exported S/M/L/XL but the source catalog has an additional XS size that was discontinued. The image column has URLs for XS/S/M/L/XL. The import matches row 1 (S) to the XS image, row 2 (M) to the S image, and so on — every variant is wearing the wrong size’s image.
2c. Prevention
Prevention: before generating the final Shopify CSV, sort the variant rows and their corresponding image URLs into the same sequence. Verify the alignment by spot-checking the Variant Image column against Option1 Value in a spreadsheet — every row’s image URL should visually correspond to that row’s option value. Then run the test import and manually verify each variant’s image in the Shopify admin.
[CODE: Example — correct vs incorrect Shopify CSV variant row structure]
# INCORRECT — Image URLs in different order than variant rows
Handle,Option1 Name,Option1 Value,Variant SKU,Variant Price,Variant Image
classic-polo,Size,S,POLO-S,29.99,https://cdn.example.com/polo-xl.jpg ← Wrong image (XL image on S row)
classic-polo,Size,M,POLO-M,29.99,https://cdn.example.com/polo-s.jpg ← Wrong image (S image on M row)
classic-polo,Size,L,POLO-L,34.99,https://cdn.example.com/polo-m.jpg ← Wrong image (M image on L row)
classic-polo,Size,XL,POLO-XL,39.99,https://cdn.example.com/polo-l.jpg ← Wrong image (L image on XL row)
# CORRECT — Image URLs aligned with their variant rows
Handle,Option1 Name,Option1 Value,Variant SKU,Variant Price,Variant Image
classic-polo,Size,S,POLO-S,29.99,https://cdn.example.com/polo-s.jpg ← Correct
classic-polo,Size,M,POLO-M,29.99,https://cdn.example.com/polo-m.jpg ← Correct
classic-polo,Size,L,POLO-L,34.99,https://cdn.example.com/polo-l.jpg ← Correct
classic-polo,Size,XL,POLO-XL,39.99,https://cdn.example.com/polo-xl.jpg ← Correct[INTERNAL LINK: → /blog/shopify-catalog-migration — section 5 covers the full variant row structure requirement in the migration walkthrough]
3. Metafield and Custom Attribute Loss: What Shopify’s Native CSV Does Not Carry
Shopify’s product CSV covers the fields that Shopify’s standard admin interface manages. Everything else does not have a column and will be silently ignored during import — no error, no warning, no indication that data was dropped.
3a. What Gets Dropped
Any custom attribute in your source system that does not map to a named column in Shopify’s CSV template is silently dropped during import. The import processes successfully from Shopify’s perspective because the custom attributes are not required fields — Shopify simply ignores columns it does not recognize in the template. What gets dropped typically includes: technical specifications (dimensions beyond weight, electrical ratings, compatibility), compliance certifications (CE, RoHS, food safety), care instructions beyond what fits in the HTML description, B2B pricing tiers, custom ERP identifiers, related product relationships, and any attribute added to the source system after the initial Shopify CSV template was created.
3b. Prevention
Prevention: inventory all custom attributes in your source system before migration. For each attribute, make a decision: does it go in Tags, in body_html, in a Shopify metafield (API-populated post-import), or is it truly irrelevant to the Shopify store and can be dropped?
Metafield population is a separate post-import operation. It requires the Shopify Admin API (GraphQL metafieldsSet mutation) or a PIM connector that handles metafield sync as part of the channel publish workflow. This step should be planned, scripted, and tested before the migration, not improvised after the catalog is live and customers are already shopping.
[INTERNAL LINK: → /blog/shopify-catalog-migration — section 7 covers the decision framework for attributes with no Shopify equivalent]
[INTERNAL LINK: → /blog/sku-management-scale — the attribute schema decisions that determine which fields are critical to preserve during migration]
4. SEO Impact: Handle Changes, URL Redirects, and What You Lose If You Skip This Step
URL redirects are the migration task most frequently deferred to “after launch.” This is the wrong order. Redirects installed after DNS cutover mean the gap between when the old URLs returned 404s and when the redirects were installed will be logged by Google’s crawler. Pages visited during that gap may be dropped from the index faster than pages that went straight from a 301 to the new URL.
[CITE: Google Search Central — how Googlebot handles 404 and soft-404 responses — developers.google.com/search/docs/crawling-indexing/http-network-errors]
[CITE: Shopify URL redirect bulk import — help.shopify.com/en/manual/online-store/menus-and-links/url-redirects#import-redirects-from-a-csv-file]
[QUOTE: Seek a practitioner quote on the SEO impact of missed redirects — e.g., from a Shopify SEO specialist or an e-commerce agency with migration experience: “We have seen sites lose 30–40% of organic traffic in the first month after a migration where redirects were incomplete. The recovery takes longer than the traffic loss — it typically takes 3–6 months to fully regain ranking positions even after redirects are fixed.”]
[E-E-A-T HOOK — Risk callout]: The claim that “rankings can take 2–4 weeks to manifest” is a general estimate and varies significantly based on crawl frequency for the specific domain. For high-authority sites, impact may be faster. For low-traffic sites, the loss may not be visible in analytics for longer. Hedge this appropriately — do not state it as a fixed timeline.
4a. The URL Change Problem
Shopify uses the handle field as the product URL slug: /products/{handle}. If your source platform used a different URL structure — Magento’s /product-name.html, WooCommerce’s /shop/product-name/, a custom platform’s /item/12345 — every product URL changes during the migration. Without 301 redirects in place at DNS cutover, all inbound links and indexed URLs return 404s. Google’s crawler logs the 404, and the pages begin dropping from the index. The ranking impact manifests over 2–4 weeks for most sites, but this estimate varies with crawl frequency — high-traffic sites may see impact within days; low-traffic sites may not see it in analytics for longer.
4b. Prevention
Prevention: export the complete list of product URLs from your source platform before the migration. Generate the corresponding Shopify /products/{handle} URL for each old URL. Import the resulting redirect map via Shopify’s URL redirect CSV import before the DNS cutover. Test a sample of redirects after import to confirm they are returning 301 status codes and pointing to the correct Shopify URLs.
4c. The Commonly Missed Case
Internal links within product descriptions and navigation menus that reference old product URLs. A product description that links to a complementary product by its old URL will be broken after migration — the redirect handles direct traffic and external links but does not automatically update hardcoded URLs within your own content. After the migration, run a find-and-replace across all product descriptions and navigation links to update old URLs to new ones.
5. Inventory Reset to Zero: Why This Happens and How to Prevent It
An inventory reset to zero is operationally devastating on launch day. Products that were in stock appear as out of stock. Customers who want to buy cannot. Backorder emails may fire for products that are not actually on backorder. The fix — running a separate inventory import — takes hours and requires live stock counts from an ERP or WMS that may not have been set up for the Shopify connection yet.
5a. Root Cause
Root cause: Shopify’s CSV writes whatever value is in the Variant Inventory Qty column at import time. If the column is blank, Shopify writes 0. If the column is populated from an export that was run weeks before launch, the values are stale. Products that shipped between the catalog export date and the launch date will show higher-than-actual inventory. Products that sold well will show inventory that no longer exists. There is no post-import correction mechanism — the values are written and become the authoritative inventory for that location.
5b. The Correct Sequencing
Shopify treats product records and inventory levels as separate objects in its data model. A ProductVariant stores the product’s attributes and options. An InventoryLevel stores the quantity available at a specific location. These two objects can be created and updated independently via the API. The correct migration sequencing exploits this separation: import the catalog (product structure, descriptions, images, variants) with the Variant Inventory Qty column explicitly blank. Then run a separate inventory import as close to launch as possible — within hours, not days — using actual stock counts from your ERP or WMS.
5c. Prevention
Prevention: explicitly blank the Variant Inventory Qty column before your catalog import CSV is generated. Do not leave it to chance or to the default behavior of your export tool. After the catalog import is complete and validated, run a dedicated inventory update via the Shopify Inventory API or a separate CSV import using actual real-time stock counts. The inventory import takes minutes; the accuracy gain compared to a weeks-old snapshot is worth the extra step.
6. Duplicate Product Creation: How to Detect It Before It Goes Live
Duplicate products corrupt search results, navigation, and reporting. A customer searching for “blue polo” sees two identical products. Analytics splits sales between two records. Inventory is tracked separately for what should be one product.
6a. Root Cause
Root cause: Shopify creates a new product for any handle value that does not already exist in the store. The most common cause of duplicates is running the import more than once — which happens during testing and is expected — without consistently deleting the test products between runs. If a test import creates products with handles classic-polo and classic-polo-1 (because Shopify auto-incremented to avoid a collision), the real import creates classic-polo again as a new product, and classic-polo-1 is left over from the test run.
A second common cause: source platform exports that generate slightly different slugs across different export runs. A product named “Classic Polo™” may export as classic-polo on one run and classic-polo-tm on another, depending on how the export tool handles the trademark symbol. Shopify creates two separate products.
6b. Detection Pre-Launch
Detection pre-launch: export the complete product list from Shopify immediately after each import, even test imports. Sort the export by title. Scan for rows where the same title appears more than once with different handles — these are duplicates. Also compare the total product count against the source system count: if the Shopify count is higher, investigate before proceeding.
7. The Staging Import Checklist: 12 Things to Verify in a Test Import Before Going Live
[E-E-A-T HOOK — Risk callout]: Run this checklist on a Shopify Development Store, not your production store. Development Stores are free for Shopify Partners and allow unlimited test imports without affecting live data or customer orders.
[E-E-A-T HOOK — Experience]: Consider adding a note after the checklist: “This checklist was developed from [N] migration reviews — steps that consistently caught failures before launch are marked [key item]. If you are resource-constrained, prioritize Steps 5 (variant image assignment) and 12 (handle collisions) first.”
Run this checklist on a Shopify Development Store, not your production store. Each numbered item is a HowTo step that maps to a specific failure mode — the step number corresponds to the failure it prevents.
Step 1: Verify Total Product Count
Total product count in Shopify after import matches the source system’s export count. Any discrepancy is evidence of duplicates, skipped records, or failed rows.
Step 2: Verify Product Distribution
Product count by type and category matches the expected distribution from the source system. A category with 0 products when 50 were expected indicates a category mapping failure.
Step 3: Spot-Check Products Across Types
Open 5 products across different product types in the Shopify admin — not just the product list view. Verify all fields are populated correctly, including description, vendor, and product_type.
Step 4: Verify Variant Counts
For each spot-checked product, verify the variant count matches the source system. A product with 4 variants in the source appearing with 3 variants in Shopify indicates a row ordering or import failure.
Step 5: Verify Variant Image Assignment
Open each variant for each spot-checked product in the Shopify admin. Verify the image displayed for each variant is the image that corresponds to that variant’s option values. Do not check only the product page — check each individual variant’s image in the admin edit view.
Step 6: Verify the 3-Option Limit Products
Test-import a product with exactly 3 option dimensions and verify all combinations are imported without truncation.
Step 7: Confirm Handle Values
Verify that handle values match the intended URL slugs. Check for encoding artifacts (special characters slugified incorrectly), unexpected truncation, and auto-incremented suffixes added by Shopify to resolve collisions.
Step 8: Check HTML Encoding in Descriptions
Open product descriptions and check for HTML encoding artifacts: curly quotes displayed as ’, em dashes as —, ampersands as &. These indicate an encoding mismatch in the description export.
Step 9: Verify Image URLs Resolved
Check that no product shows a broken image placeholder. In the admin, look for the image count per product and verify each image loads. A product with 3 images shown as a count but a placeholder in the gallery indicates a 404 URL during import.
Step 10: Confirm Product Status
Confirm products defaulted to draft (not active) after import. All products should be in draft status after a test import and reviewed before being set to active.
Step 11: Check the Import Error Log
Download the import error log from the Shopify admin. Any row-level errors — even for records that appear in the catalog — should be investigated before the production import.
Step 12: Verify No Handle Collisions
Compare the product count against the expected count. Export the product list and check for any handles with a numeric suffix (-1, -2) that Shopify added to resolve collisions with existing records.
[INTERNAL LINK: → /blog/shopify-catalog-migration — the full migration process that the staging checklist supports]
8. How a PIM Prevents These Failures by Acting as a Clean, Validated Data Source
A PIM staging layer addresses the structural root cause of each failure mode — not by adding review steps, but by transforming the data into the correct format before it touches Shopify.
8a. What a PIM Prevents Per Failure Mode
Variant image ordering: a PIM that exports to Shopify CSV format generates correctly ordered variant rows with image URLs matched to the correct variant record. The ordering is produced programmatically from the PIM’s parent-variant data model, not derived from the source exporter’s arbitrary row sequence.
Metafield loss: a PIM maps custom attributes to metafield targets before export. The metafield population step is configured as part of the PIM-to-Shopify sync workflow, not improvised post-import.
Inventory separation: a PIM exports catalog and inventory as separate operations. The catalog export explicitly omits inventory columns; the inventory export runs separately on a pre-launch schedule.
Duplicate detection: a PIM deduplicates by SKU or GTIN before data enters Shopify. Products with the same identifier are updated, not duplicated.
8b. The Ongoing Benefit
After migration, the PIM remains as the system of record. Shopify becomes a publishing channel, and the migration work — the field mapping configuration, the variant structure, the metafield definitions — is reused indefinitely as the catalog evolves. Future changes to the catalog flow from the PIM to Shopify automatically, and the staging import validation that caught these failure modes during migration is applied on every subsequent sync.
[CTA — after intro (soft): “See how MicroPIM structures data to catch migration failures before they reach Shopify.” [INTERNAL LINK: → /how-it-works]]
[CTA — after section 7 (medium): “Run your migration validation checklist inside MicroPIM — completeness scoring and duplicate detection run before you export.”]
[CTA — after FAQ (hard): “Validate your catalog data in MicroPIM before it reaches Shopify. Catch misassigned images, custom attribute loss, and duplicate handles in a test run — before launch day.”]
Frequently Asked Questions
Schema note: Mark this section with FAQPage JSON-LD. Each H3 question + answer pair maps to one FAQPage mainEntity item.
Why do variant images get assigned to the wrong variants in Shopify?
Shopify’s CSV format assigns variant images based on row position: the Variant Image URL on a given row is assigned to the variant whose option values appear on that same row. If the exporter outputs variants in a different order than the image URLs expect, images land on the wrong variants. No error is generated — the import succeeds. Prevention requires sorting variant rows and image URLs into the same sequence before the import, then manually verifying each variant’s image in the Shopify admin after a test import.
What custom data gets lost in a Shopify CSV migration?
Shopify’s product CSV has no column for metafields, so any custom attribute that does not map to a standard Shopify field — product_type, vendor, tags, body_html, or variant option columns — is silently dropped during import. Typical losses include: technical specifications, compliance certifications, care instructions, B2B pricing tiers, and custom ERP identifiers. These must be populated via the Shopify Admin API (GraphQL metafieldsSet mutation) as a separate post-import step — a step that should be planned before the migration, not improvised afterward.
How do I prevent inventory from resetting to zero during a Shopify migration?
Separate catalog and inventory migration into two distinct operations. Import the product catalog first with the Variant Inventory Qty column left blank. Then run a dedicated inventory import as close to launch as possible — within hours, not days — using actual stock counts from your ERP or WMS. Shopify’s product variant and inventory level are separate API objects and can be updated independently; exploiting this separation is the correct approach for all but the smallest catalogs.
How does a Shopify migration affect SEO rankings?
A Shopify migration damages SEO rankings when product URLs change without 301 redirects in place at launch — all previously indexed URLs return 404s and Google begins dropping them from the index. The ranking impact typically manifests over 2–4 weeks, though this varies significantly with the site’s crawl frequency and domain authority. Prevention requires mapping every source platform URL to its corresponding new Shopify handle URL and importing the redirect map via Shopify’s URL redirect CSV before DNS cutover.
What causes duplicate products in Shopify after a CSV import?
Duplicate products occur when the import runs more than once with different handle values for the same product, or when the source platform generates slightly different slugs for the same product across different export runs. Shopify creates a new product for any handle that does not already exist in the store. Detection: compare the total product count in Shopify immediately after import against the expected count from the source system. Export the full product list and sort by title to identify products appearing twice with different handles.
Estimated word count: 1,800

