Available for projects & agency overflow · Quick reply, from the person who does the work

Duplicating a WordPress site to staging

Testing an update or a development on a faithful copy of the site, before touching production, almost always means changing the URL (site.fr to preprod.site.fr or a subfolder). That URL change is the most commonly mishandled technical point of this kind of copy.

Describe my issue Send a message

Why changing the URL breaks settings if done wrong

WordPress stores some of its data (theme settings, widget configuration, certain metadata, plugin options) as serialised PHP data in the MySQL database’s text columns. A serialised string encodes the exact length of each substring it contains, for example s:19:"https://old-site.fr". If the URL is replaced with a plain SQL search-and-replace, using a query like UPDATE wp_options SET option_value = REPLACE(...), the declared number before the quotes no longer matches the new string length, and WordPress fails to unserialise the data.

A staging copy multiplies the chances of falling into this trap, because the URL often changes a second time afterwards: a temporary test address at copy time, then a permanent staging address once the environment settles. Every change has to go through the same tool, not just the first one.

The result isn’t always visible straight away: reset theme settings, disappearing widgets, emptied plugin options, sometimes without a clear error message. The correct method uses a tool that recalculates these lengths on every replacement, typically WP-CLI’s wp search-replace old-url new-url --all-tables command, or a migration plugin that does this work internally, such as All-in-One WP Migration or WP Migrate DB.

What to plan for beyond a standard copy

  • Blocking search engine indexing: indexed duplicate content harms the main site’s rankings
  • Cutting real email sending (order confirmations, notifications) so no real customer is alerted during testing
  • Neutralising payment gateways by keeping them strictly in test mode, so a real payment is never triggered
  • A growing gap between staging and production over time if no regular resync is planned

How I run a staging duplication

  1. Full copy of files and database

    I duplicate all site files and export the database to the staging environment.

  2. URL replacement with wp search-replace

    The production URL is replaced with the staging one using WP-CLI, which correctly recalculates serialised data lengths.

  3. Blocking indexing

    I add a noindex tag or a dedicated robots.txt for staging, so no search engine indexes the duplicate.

  4. Neutralising outgoing emails

    I use an email capture service or disable the sending plugin, so no notification reaches a real customer from staging.

  5. Switching payment gateways to test mode

    Real payment credentials are swapped for their test equivalents, so no real money movement is ever triggered.

  6. Resyncing when needed

    If the gap between staging and production grows too large over time, I run a full copy from production again rather than patching staging case by case.

Related reading

Describe your need in one minute

A few targeted questions so I can reply with an estimate rather than another questionnaire.

origine
catalogue
extensions-premium (facultatif)
conserver (facultatif)
Please provide an email or a phone number so I can get back to you.

Please provide an email or a phone number so I can get back to you.

Frequently asked questions

Why does my staging site show up in Google when I never shared it?
Without a noindex tag or a dedicated robots.txt file, search engines can discover and index staging like any public site, creating duplicate content that harms the main site’s rankings.
Could a real customer receive an email from my staging tests?
Yes, if email sending isn’t cut off. That’s why I disable the sending plugin or use an email capture service before starting to test orders on staging.
Can I just use a plain SQL copy-paste to change the URL on staging?
No. WordPress serialises some data in the database, encoding the exact length of each string. A plain text replace breaks these lengths and silently corrupts theme and plugin settings.
Do I need to redo a full copy for every test?
Not systematically, but if the gap between staging and production grows large over time, a full resync avoids patching differences one by one.
Could a real payment be triggered during a staging test?
Only if the payment gateway stays configured in live mode. I always swap real credentials for their test equivalents before any work on the checkout.