Skip to content
WP Cloud
WP Cloud
    • For Hosts
    • For Agencies
    • For Registrars
    • For Native Hosting
    • Performance
    • Security
    • Real-Time Automated Failover
    • Vertical Scaling and Bursting
    • WordPress Management
    • PanelAlpha Integration: White-Label WordPress Control Panel for Hosts
    • EasyEngine Panel Integration: Visual WordPress Management for WP Cloud
    • FAQs
    • WP Cloud API
    • Partner Portal
    • Documentation
    • New Partner Guide
    • Pressable
    • Convesio
    • Porkbun
    • PanelAlpha
    • Ivapix
    • UNC Greensboro
    • Impressive Hosting
    • Blog
    • Performance Benchmarks
  • Connect With Us
  • Login ↗
Start Here ↗
  • Solutions

    • For Hosts
    • For Agencies
    • For Registrars
    • For Native Hosting
    • Featured Partners

    Features

    • Performance
    • Security
    • Real-Time Automated Failover
    • Vertical Scaling and Bursting
    • WordPress Management

    Integrations

    • PanelAlpha Integration
    • Easy Engine Panel Integration

    Resources

    • FAQs
    • WP Cloud API
    • Partner Portal
    • Documentation
    • New Partner Guide
  • Case Studies
    • PressableA case study about how WP Cloud supports Pressable to power millions of page views daily.
    • Convesio
    • Porkbun
    • PanelAlpha
    • Ivapix
    • UNC Greensboro
    • Newspack
    • Inverse Paradox
  • Insights
    • Podcast
    • BlogWP Cloud blog page with latest news and updates about the platform.
    • Performance Benchmarks
  • Connect With Us
  • Login ↗
Start Here ↗

Browse

    • WP Cloud platform overview
    • Onboard and launch with WP Cloud
    • WP Cloud Partner Portal
    • Get support from WP Cloud
    • WP Cloud glossary
    • Manage and secure API keys
    • Client SSH
    • WP Cloud API quick start
    • Webhooks
    • Run bulk tasks across sites
      • Manage site domains and aliases
      • Domain verification records
      • TLS certificates
      • Manage custom TLS certificates
      • Cloudflare and WP Cloud
    • Clone a site
    • Configure resources, site type, and billing with site meta
    • Delete a site
    • Persistent data
    • Staging sites
    • Migrate a site to WP Cloud
      • SSH and SFTP access models
      • Client SSH
      • User SSH and SFTP access
      • Database credentials
      • phpMyAdmin
      • ABSPATH
      • Default wp-config.php
      • Site constants
      • Configure redirects and headers with custom-redirects.php
      • Akismet and Jetpack
      • Blocked and unsupported plugins
      • PHP lifecycle and supported versions
      • Symlinks and managed software
      • WordPress versions
      • Install Composer and WP-CLI packages
      • Manage platform software with WP-CLI
      • Useful WP-CLI commands
    • Transactional email
    • WordPress multisite
    • Cron scheduling
    • Decoupled and headless WordPress
    • Repair Yoast indexables
      • Page Cache
      • Edge Cache
      • Object Cache
      • Image transformation
      • Offload image sub-sizes
    • Configure lightweight 404s for static files
      • DDoS protection
      • Defensive Mode
      • Rate limiting
      • Network and web application firewalls
      • Bot protection
      • Password protection
      • HTTP and security headers
      • PHP filesystem access permissions
      • Scan a site for malware
    • Backups overview
    • Create an on-demand backup
    • Restore a backup
    • Jetpack backups
      • Error logs
      • Web server logs
    • Metrics
    • Application performance monitoring
    • Automated failover
    • IP ranges
    • Origin and edge servers
    • Server specifications and settings
    • EasyEngine integration
    • PanelAlpha integration
      • White labelling and co-marketing WP Cloud
      • WP Cloud logos
      • Terms of Service & Compliance
      • Prohibited content
      • Copyright infringement and takedown notifications
    • WP Cloud billing
    • WP Cloud for agencies and site networks
    • WP Cloud partner support options
    • Troubleshoot Page and Edge Cache
    • Troubleshoot HTTP 429 and 599 errors
    • WP Cloud HTTP status codes
    • Troubleshoot site performance
    • Cache slow database queries
    • Troubleshoot duplicate core files, wp-config.php, and wp-admin 403 errors
    • Troubleshoot email delivery
    • Troubleshoot PDF thumbnail generation
    • Troubleshoot TLS certificate provisioning
Documentation/Migrations/Migrate a site to WP Cloud

Migrate a site to WP Cloud

LAST UPDATED

3 months ago

    WP Cloud includes native migration tooling that copies a WordPress site from a remote server over SSH into a destination site in the partner’s WP Cloud account. It supports one-off site moves and repeated migrations used to refresh a destination before production cutover.

    The remote hosting environment must provide enough access for WP Cloud to connect and run the migration. Some hosting configurations or complex installations may not be compatible.

    Requirements

    The remote server must provide:

    • SSH shell access using a username and password, a username and identity file, or a username and passphrase-protected identity file;
    • WP-CLI support, or an environment where the migration can supply WP-CLI; and
    • rsync.

    Collect the following connection values before creating the migration:

    • remote-host: SSH hostname.
    • remote-user: SSH username.
    • remote-port: SSH port, which defaults to 22.
    • remote-domain: Optional source domain when it differs from the destination hostname.
    • remote-docroot: Optional path to the source document root. WP Cloud attempts common paths when it is omitted.
    • remote-pass: Password when password authentication is used.
    • ssh-id: Identity-file contents when key authentication is used.
    • ssh-id-pass: Passphrase when the identity file is protected.

    Treat passwords, private keys, and passphrases as credentials. Do not put them in logs, screenshots, support requests, or customer-visible responses.

    Use one supported authentication combination for each migration. Supply remote-pass for password authentication. Supply ssh-id for identity-file authentication and add ssh-id-pass only when that identity is protected by a passphrase. When remote-domain is an empty value, the migration uses the site’s default domain. When remote-docroot is absent, WP Cloud tries common document-root paths on the remote host.

    Prepare the destination

    Create a new destination site when possible. A new site avoids overwriting an existing site and can be created with allow_site_migration enabled.

    Warning: Enabling an existing site as an SSH migration target accepts destructive replacement of its files and database. The current operation cannot be undone. Preserve the existing site and confirm the destination ID before continuing.

    For an existing destination, send a POST request to the Configure a site to accept an incoming SSH migration endpoint:

    export WP_CLOUD_SITE='destination-domain-or-ID'
    
    curl --fail-with-body --silent --show-error \
      --request POST \
      --header 'Auth: API_AUTH_TOKEN' \
      "https://atomic-api.wordpress.com/api/v1.0/site-allow-ssh-migration/${WP_CLOUD_SITE}"Code language: JavaScript (javascript)

    A successful response reports that the site is ready for a migration. This operation only enables the destination; it does not start the migration. After a migration starts, allow_site_migration changes to the migration ID and prevents another migration from targeting the site at the same time.

    Create and update the migration

    Create the migration with GET /migration/create/{site_id_or_domain} and supply the remote connection values. The operation returns a migration ID. Keep that ID with the destination site record because later updates, preflight checks, and migration runs use it.

    If you do not provide an SSH identity, the migration creates a public key and returns it as ssh-id-pub. Add that public key to the remote user’s authorized_keys file before preflight checks.

    Update the migration with GET /migration/update/{migration-id} as the site owner supplies corrected host, user, document-root, domain, or authentication values. Migration details cannot be changed while the migration is actively running; pause it before changing connection data. Sensitive values such as the private identity and remote password must remain redacted when migration details are displayed.

    The migration record should identify the remote host, remote user, remote port, optional remote domain, optional document root, destination site, and authentication method without exposing credential values. Confirm that the destination in this record matches the site prepared for migration before starting preflight.

    Run preflight checks

    Start a preflight with GET /migration/preflight/{migration-id} after the remote credentials and destination are ready. Each preflight returns a new response ticket. Use the result to correct connection, document-root, WP-CLI, or rsync problems, then update the migration and run preflight again.

    After a preflight, return to Create and update the migration when you need to correct or replace migration information. You can update the migration and run preflight again as many times as necessary before starting the migration.

    Check logs and status

    Preflight checks and migration runs return response tickets. If webhooks are configured, they report response-ticket updates. You can also poll the response-ticket endpoints directly.

    Use the Get Response Ticket Summary endpoint for its state, or the Get Response Ticket Details endpoint when you need its messages. Both operations accept the ticket in the form-encoded response-ticket-id field.

    export WP_CLOUD_RESPONSE_TICKET='<response-ticket-id>'
    
    curl --fail-with-body --silent --show-error \
      --request POST \
      --header 'Auth: API_AUTH_TOKEN' \
      --header 'Content-Type: application/x-www-form-urlencoded' \
      --data-urlencode "response-ticket-id=${WP_CLOUD_RESPONSE_TICKET}" \
      'https://atomic-api.wordpress.com/api/v1.0/response-ticket/get/summary'Code language: JavaScript (javascript)

    A response-ticket request returns 202 when no response is available yet; retry after one second. A completed ticket reports success or failure, while active work reports running.

    Use the full operation only when the summary is not enough:

    curl --fail-with-body --silent --show-error \
      --request POST \
      --header 'Auth: API_AUTH_TOKEN' \
      --header 'Content-Type: application/x-www-form-urlencoded' \
      --data-urlencode "response-ticket-id=${WP_CLOUD_RESPONSE_TICKET}" \
      'https://atomic-api.wordpress.com/api/v1.0/response-ticket/get/full'Code language: JavaScript (javascript)

    A 400 response means the request omitted the ticket ID. A 404 response means the ticket was not found. Store the migration ID separately from each response ticket because a new preflight or migration attempt returns a new ticket.

    Keep each new response ticket with the preflight attempt that created it. The summary provides the current state and response count; the full response provides the attached messages. Use those messages to distinguish an authentication failure from a missing document root, unavailable WP-CLI, or unavailable rsync before changing migration data.

    Run and monitor the migration

    Proceed only after preflight succeeds. Mark the migration ready to run with GET /migration/ready/{migration-id}. The operation starts the migration and returns a new response ticket. Monitor it through configured webhooks or the response-ticket endpoints until it reports success or failure.

    The migration is ready for cutover only after the response ticket reports success and the destination has been checked for the expected content, domain behavior, users, plugins, theme, and customer-facing functions.

    Retry or refresh a migration

    After a preflight, return to the migration update step when you need to correct connection or source information. Run preflight again after every update instead of relying on an earlier successful result.

    After a migration reports success or failure, you can repeat the update, preflight, migration, and monitoring steps as necessary. Repeat the workflow after a failure to troubleshoot a corrected configuration, or after a successful migration to copy changes made on the source site before production cutover.

    Warning: Every retry or refresh is destructive to the destination because it pulls the source filesystem and database into the destination again. Preserve destination-only changes or move them back to the source before another run. A refresh is another full destination-changing operation, not an incremental confirmation.

    Migration API operations

    The migration operations below are still being tested and are not yet included in the public WP Cloud API reference. Their contracts may change. They are documented here temporarily so partners can build and test the native migration workflow.

    Create a migration

    GET /migration/create/{site_id_or_domain}

    This operation starts a new site migration and returns a migration ID.

    Request fields:

    • remote-host: Hostname of the remote server.
    • remote-port: Optional SSH port. The default is 22.
    • remote-user: Username used to connect to the remote server.
    • remote-pass: Optional password when password authentication is used.
    • remote-docroot: Optional path to the remote site’s document root.
    • remote-domain: Optional source domain when it differs from the destination site’s domain.
    • ssh-id: Optional SSH private-key data.
    • ssh-id-pass: Optional passphrase for the supplied SSH private key.

    If ssh-id is omitted, WP Cloud generates an SSH identity for the migration and returns the public key as ssh-id-pub. Add that public key to the remote user’s authorized_keys file before running preflight checks.

    Get migration details

    GET /migration/get/{migration-id}

    This operation returns the current migration details. Sensitive values such as ssh-id and remote-pass are redacted.

    • migration-id: Migration to retrieve.

    Update a migration

    GET /migration/update/{migration-id}

    This operation updates an existing migration. A migration cannot be updated while it is actively running; pause it before changing its details.

    • migration-id: Migration to update.
    • ssh-id: Optional replacement SSH private-key data.
    • ssh-id-pass: Optional passphrase for the supplied SSH private key.
    • remote-host: Optional replacement remote hostname.
    • remote-port: Optional replacement SSH port. The default is 22.
    • remote-user: Optional replacement remote username.
    • remote-pass: Optional replacement password.
    • remote-docroot: Optional replacement remote document-root path.
    • remote-domain: Optional replacement source domain. An explicitly supplied empty value uses the destination site’s default domain.

    Set a migration to ready

    GET /migration/ready/{migration-id}

    This operation marks a migration as ready to run and returns a new response ticket.

    • migration-id: Migration to run.

    Run preflight checks

    GET /migration/preflight/{migration-id}

    This operation tests the saved connection and migration information before the migration runs. Each preflight attempt returns a new response ticket.

    • migration-id: Migration to test.
    Previous Staging sites
    Next SSH and SFTP access models

    Related Guides

    On this page

      Contact support

      Contact us with Support issues and questions related to WP Cloud, the WP Cloud Atomic API, API-key IP allow list changes, Station, and more.

      Check the FAQs

      Have questions? Please visit our FAQ to learn more.

      An Automattic venture

      Work With Us

      Press

      Privacy Policy

      © 2021-2026 Automattic Inc.

      Notifications