TL;DR
WordPress throws Missing a temporary folder. when PHP's temporary upload directory is missing, unset, or not writable. The quickest fix is adding one line to wp-config.php:
define('WP_TEMP_DIR', ABSPATH . 'wp-content/temp/');
Then create the directory and set the right permissions:
mkdir -p /var/www/html/wp-content/temp
chmod 755 /var/www/html/wp-content/temp
chown www-data:www-data /var/www/html/wp-content/temp
Still broken? The real culprit is probably in your php.ini โ keep reading.
What Causes This Error
Every time you upload an image or install a plugin, PHP writes the file to a temp directory first. WordPress then moves it to its final destination. This error fires when PHP can't find anywhere valid to stage that temporary file.
Almost always, it's one of three things:
- The
upload_tmp_dirdirective inphp.inipoints to a path that doesn't exist. Very common on VPS setups where someone customized the default and then the directory never got created. - The temp directory exists, but the web server user can't write to it. PHP fails silently in this case โ no useful error, just this cryptic message.
upload_tmp_diris empty or undefined, so PHP falls back to/tmpโ but/tmpis blocked byopen_basediror mounted withnoexec.
Step 1 โ Find Out What PHP Is Actually Using
Before touching any config, confirm what PHP sees as its temp directory. Upload this file to your WordPress root via FTP or SSH:
<?php
echo 'upload_tmp_dir: ' . ini_get('upload_tmp_dir') . "\n";
echo 'sys_get_temp_dir: ' . sys_get_temp_dir() . "\n";
echo 'WP_TEMP_DIR: ' . (defined('WP_TEMP_DIR') ? WP_TEMP_DIR : 'not defined') . "\n";
?>
Visit https://yoursite.com/check-tmp.php and note the output. Delete this file immediately after โ never leave debug scripts on a live server.
If upload_tmp_dir shows a path like /var/php_tmp that doesn't actually exist, you've found your problem.
Step 2 โ Fix via wp-config.php (Works Everywhere)
This is the recommended starting point. It overrides whatever PHP is configured with, which means it works even on shared hosting where you can't touch php.ini.
Open wp-config.php and add this line before /* That's all, stop editing! */:
define('WP_TEMP_DIR', ABSPATH . 'wp-content/temp/');
Now create the directory. Adjust the path to match your actual WordPress root:
mkdir -p /var/www/html/wp-content/temp
chmod 755 /var/www/html/wp-content/temp
# Apache:
chown www-data:www-data /var/www/html/wp-content/temp
# Nginx + PHP-FPM (user varies by setup):
# chown nginx:nginx /var/www/html/wp-content/temp
# chown php-fpm-user:php-fpm-user /var/www/html/wp-content/temp
Not sure which user PHP runs as? This command will tell you:
ps aux | grep -E '(apache|nginx|php-fpm|httpd)' | grep -v root | head -1
Step 3 โ Fix via php.ini (VPS / Dedicated Server)
Got SSH access? Editing php.ini directly is cleaner than the wp-config.php workaround โ it fixes the issue at the PHP level rather than patching around it.
Find the active config file:
php --ini | grep 'Loaded Configuration'
Open that file and set upload_tmp_dir to a real, writable path:
upload_tmp_dir = /tmp
Verify /tmp looks right:
ls -la /tmp
# Normal output: drwxrwxrwt โ the sticky bit (t) is expected here
Using a custom path instead? Create it first:
mkdir -p /var/php_tmp
chmod 1777 /var/php_tmp
Restart your web stack after saving the change:
# PHP-FPM (adjust version number):
sudo systemctl restart php8.2-fpm
# Apache with mod_php:
sudo systemctl restart apache2
Step 4 โ Fix via .htaccess (Shared Hosting / Apache)
On shared hosting with no php.ini access, Apache lets you override some PHP settings through .htaccess. Add this to your WordPress root .htaccess:
php_value upload_tmp_dir /tmp
Fair warning: some hosts lock down which PHP values you can override this way. If nothing changes after adding that line, fall back to the wp-config.php approach in Step 2 โ it's more reliable.
Step 5 โ Check open_basedir Restrictions
Hardened servers and many shared hosts use open_basedir to limit which directories PHP can touch. If your temp directory isn't in the allowed list, PHP can't write to it โ even if permissions are perfect.
Check what's currently restricted:
php -r "echo ini_get('open_basedir');"
See a path list that excludes /tmp or your chosen temp dir? Two options:
- Add the temp directory to
open_basedirinphp.inior your server config - Point
WP_TEMP_DIRto a path already inside the allowed list โ somewhere under your WordPress root works well
# Example: allow both the site root and /tmp
open_basedir = /var/www/html:/tmp
Verification โ Confirm the Fix Worked
Test with an actual upload rather than guessing:
- Go to WordPress Admin โ Media โ Add New
- Upload any image โ a small JPEG or PNG is fine
- No error? The fix worked
- Also test plugin install: Plugins โ Add New, search for something lightweight like "Hello Dolly" and install it
For a definitive check, run a write test as the web server user directly over SSH:
sudo -u www-data touch /var/www/html/wp-content/temp/test.txt && echo "Writable" || echo "Not writable"
rm -f /var/www/html/wp-content/temp/test.txt
Writable means you're done. Not writable means the ownership or permissions are still off โ re-check the chown step.
Quick Checklist
- Temp directory path exists on disk
- Web server user (www-data, nginx, etc.) owns the directory
- Permissions are at least
755 - Path is not blocked by
open_basedir - PHP or Apache restarted after any
php.inichanges - Debug file (
check-tmp.php) deleted from server

