The migration finished. DNS is pointed. You log in and WordPress asks for FTP credentials to install a plugin. Or updates work but image uploads fail. Or everything looks fine until you try to save wp-config and get a permission denied error in the logs.
File ownership and permissions are the unglamorous part of every WordPress move. Copy tools preserve or break them. A new server uses a different web user than the old host. Getting this wrong is not a "WordPress bug." It is Linux being literal.
What WordPress needs in general
Typical guidance on Linux hosting:
- Directories: 755 (owner can write, web server can read and traverse)
- Files: 644 (owner writes, web server reads)
- wp-config.php: tighter, often 640 or 600 so other users on shared systems cannot read database passwords
- wp-content/uploads: must be writable by the user PHP runs as so media uploads work
Exact numbers vary by host. cPanel might use your account user plus a group the web server shares. Some VPS setups run PHP-FPM as www-data while files belong to your deploy user. The rule is: the PHP process must be able to read WordPress and write where it needs to (uploads, cache dirs, some plugin folders).
What goes wrong after migration
- Files owned by root because you unpacked a tarball as root over SSH
- Wrong user from rsync (copied from old host with UID that does not exist on the new box)
- Too open (777) on uploads or plugins after a quick "fix" that creates security holes
- Too tight (444 or 550) so the web server cannot read theme files or write caches
- SUEXEC / PHP-FPM pool user does not match file owner, so WordPress falls back to FTP credentials prompt
- SELinux or AppArmor on some images blocking writes even when chmod looks correct (less common on typical Canadian VPS images, but it happens)
Symptoms map cleanly: white screen plus permission denied in error log, plugin install asks for FTP, broken thumbnails, cache plugins cannot create folders, backup plugins fail mid-run.
Fix ownership before you chase chmod
On a VPS, find who runs PHP (your host docs or ps aux | grep php-fpm). Often www-data, nginx, or your cPanel user.
Then set ownership on the site root recursively to a sane pair, for example your deploy user plus the web group your host documents. Do not blindly chown -R www-data:www-data unless your host tells you to; it can break SSH deploy keys and Git pull workflows.
After ownership is correct, reset permissions with a script or careful find/chmod. Many hosts publish a WordPress permissions recipe in their knowledge base. Use theirs before a random Stack Overflow answer.
A safe post-migration permission pass
- Backup first. You are about to touch every file.
- Fix owner and group on the WordPress root (files and directories).
- Directories 755, files 644 under the install (automation via find is fine if you exclude oddballs intentionally).
- Lock down
wp-config.php(600 or 640 per host policy). - Confirm
wp-content/uploadsis writable; test with a real image upload. - Check plugin cache paths (W3 Total Cache, WP Rocket, etc.) if those plugins are active.
- Try core/plugin update on staging before production.
Our pre-migration checklist helps before cutover; this pass is the "first hour on the new server" companion.
When WordPress asks for FTP credentials
That prompt means WordPress does not think it can write to wp-content directly. Fixes:
- Correct ownership so the PHP user owns or group-writes the tree
- Define
FS_METHODas'direct'in wp-config only after permissions are actually correct (masking bad perms with direct can still fail updates) - Avoid storing FTP passwords in wp-config unless you have no other option
On managed WordPress hosting, if you still see the FTP screen, open a ticket. Something is off in the pool user mapping.
Security vs convenience
777 on uploads is a lazy fix that lets any local user or compromised script write anywhere in that tree. Prefer correct owner/group.
Keep wp-config.php out of version control and out of world-readable perms. After migration, confirm it did not land in a public backup zip in wp-content (we have seen that more than once).
If you migrated from a compromised site, fix permissions during hardening, not only malware removal. See WordPress hacked: first 48 hours.
Shared hosting vs VPS
Shared/cPanel: Use the panel's "Fix permissions" tool if available. File manager uploads sometimes create files owned only by you while PHP runs as a different user; support can normalize.
VPS: You own the problem. Document the user model (deploy user, PHP-FPM pool, group membership) in your internal runbook so the next migration is not guesswork.
Bottom line
After every migration, verify ownership matches how PHP runs on the new server, then apply standard directory and file modes, tighten wp-config, and test uploads and updates. Five minutes here prevents weird support tickets for weeks.
Moving WordPress to Canadian hosting and want permissions checked as part of go-live? Talk with Swift Host. We migrate sites regularly and prefer boring chmod over emergency 777.