Una din problemele cu care mă confrunt frecvent este aceea de a migra o instanță de WordPress de pe un domeniu pe altul (e.g. din live în development). La site-uri simple este o operațiune rapidă, wp search-replace url.vechi url.nou
, dar lucrurile se complică atunci când este un multisite și/sau are o bază de date imensă.
WP are o mulțime de string-uri serializate în baza de date, deci nu e o soluție atât de simplă să faci un search/replace în dump-ul sql. Prin urmare, vom folosi wp-cli
. Pentru că sunt pe Windows, vom folosi PowerShell.
Cum ne interesează ca, în primul rând, să avem o copie funcțională pe local, nu vrem neapărat să înlocuim toate string-urile. Prin urmare, putem sări anumite tabele mai puțin importante. Treaba asta nu reprezintă o problemă foarte mare la o bază de date mică, dar la o DB măricică operațiile de search-replace
pot dura ore. (am un multi-site cu aproape 20 de sub-site-uri, DB bate spre 20Gb, am încercat să înlocuiesc toate string-urile și după 30h încă nu terminase…)
Salvezi codul de mai jos într-un fișier, să-i zicem migrate.ps1
, și ajustezi primele linii:
$wpPath
este directorul în care este instanța de WP. Dacă este în directorul din care rulezi scriptul de mai jos, un.
este suficient.$network_sites
este un array de forma"site vechi" => "site nou"
. Este important să avem//
la început pentru a evita înlocuirile în subdomenii, de exemplu. Dacă site-urile auwww
în față, adaugi și aia.$primarySiteURL
este site-ul principal$tables_to_skip
sunt tabelele în care nu vrei să se facă înlocuirile. De cele mai multe ori este safe să sari peste astea (și peste altele, dar astea sunt cele mai mari).
$wpPath = '.'
$network_sites = @{
"//live-site.url" = "//local-site.url";
"//subdomain.live-site.url" = "//subdomain.local-site.url";
}
$primarySiteURL = $network_sites["live-site.url"]
$tables_to_skip = "$($dbPrefix)posts,$($dbPrefix)postmeta,'$($dbPrefix)*_posts','$($dbPrefix)*_postmeta','$($dbPrefix)nf3_*','$($dbPrefix)*_nf3_*'"
Să reflecte necesitățile (e.g. poate ai totuși nevoie să înlocuiești datele în postmeta`
Adițional, ajustezi comenzile specifice plugin-urilor tale: elementor, wpml, ce mai ai tu. La sfârșit rulezi scriptul din terminal: ./migrate.ps1
.
$wpPath = '.'
$network_sites = @{
"//live-site.url" = "//local-site.url";
"//subdomain.live-site.url" = "//subdomain.local-site.url";
}
$primarySiteURL = $network_sites["live-site.url"]
$dbPrefix=$(wp config get table_prefix --path=$wpPath)
$tables_to_skip = "$($dbPrefix)posts,$($dbPrefix)postmeta,'$($dbPrefix)*_posts','$($dbPrefix)*_postmeta','$($dbPrefix)nf3_*','$($dbPrefix)*_nf3_*'"
$network_sites.GetEnumerator() | ForEach-Object {
$old_site_url = $_.Key
$new_site_url = $_.Value
Invoke-Expression "wp db query ""UPDATE $($dbPrefix)blogs SET domain = '$new_site_url' WHERE domain = '$old_site_url';"" --path=""$wpPath"""
$old_site_url = "https://$old_site_url"
$new_site_url = "https://$new_site_url"
$wp_cmd = "wp search-replace $old_site_url $new_site_url --path=""$wpPath"" --skip-tables=$tables_to_skip"
echo "Replacing strings in $old_site_url site"
Invoke-Expression "$wp_cmd --url=$new_site_url"
echo "Replacing strings across network"
Invoke-Expression "$wp_cmd --network"
# echo "Replacing Elementor URLs $old_site_url -> $new_site_url"
# wp elementor replace_urls $old_site_url $new_site_url --path="$wpPath"
# echo "Clear WPML cache"
# wp wpml clear-cache --url=$new_site_url --path="$wpPath"
echo "Delete transients & WP Cache"
# wp rocket clean --confirm --url=$new_site_url --path="$wpPath"
wp transient delete --all --url=$new_site_url --path="$wpPath"
wp cache flush --url=$new_site_url --path="$wpPath"
}
# echo "Flush Elementor Cache & CSS"
# wp elementor library sync --network --allow-root --path="$wpPath"
# wp elementor flush_css --network --allow-root --path="$wpPath"
# echo "Clear WPML cache"
# wp wpml clear-cache --network --allow-root --path="$wpPath"
echo "Delete transients & WP Cache"
wp transient delete --all --network --allow-root --path="$wpPath"
wp cache flush --network --allow-root --path="$wpPath"
wp network meta set 1 siteurl "https://{$primarySiteURL}/"
Bonus: execută o comandă pe toate sub-site-urile
Uneori este nevoie să execuți o comandă în wp-cli pe toate site-urile. Faci un fișiere wpms.ps1
, îl plasezi în PATH
și pui în el:
$allArgs = $PsBoundParameters.Values + $args
wp site list --field=url | ForEach-Object {
echo "running wp $allArgs --url=$_"
Invoke-Expression "wp $allArgs --url=$_"
}
Lasă un răspuns