WordPress Images Not Showing: Find the Layer That Broke
Broken images have four possible causes: the file is gone, the URL is wrong, the server refuses to serve it, or a plugin rewrote the path. Test the image URL directly to find out which.
Quick fix: right-click a broken image, copy its URL, and open it in a new tab. What you see there tells you which layer failed — a 404 means the file or path is wrong, a 403 means the server is refusing, and a working image means the problem is in the page's HTML or a script.
Do that first. Re-uploading images before this test wastes time and often does not help.
Read the direct URL result
| Result at the image URL | Cause |
|---|---|
| 404 Not Found | File missing, wrong path, or wrong site URL stored in the database |
| 403 Forbidden | File or directory permissions, or hotlink protection |
| The image loads normally | Page HTML, lazy loading, or a script error on the page |
| A redirect to the homepage | The upload path does not exist and the router caught the request |
| Broken only over HTTPS | Mixed content or a certificate covering only one hostname |
Case 1: 404 — the file or path is wrong
Open the site over SFTP or the host's file manager and look in wp-content/uploads/, then into the year and month folder from the URL. Three outcomes:
The file is there. The stored URL is wrong. This is typical after a migration or a domain change. Check Settings → General for the correct site and home URLs, then run a database search-and-replace for the old domain with a tool that handles serialised data — a plain SQL REPLACE corrupts serialised option values.
The folder is there but empty. Files were not copied during a move. Restore wp-content/uploads/ from a backup; the database rows are already correct and the images will reappear.
No uploads folder at all. Create it, and check the path under Settings → Media or the UPLOADS constant in wp-config.php.
Case 2: 403 — the server refuses to serve the file
Check ownership and permissions on wp-content/uploads. Directories normally need 755 and files 644, owned by the web server user your host uses. Mass-changing permissions to 777 is not a fix and creates a real security problem.
Then check for rules that block image requests:
- hotlink protection at the host or CDN, which blocks requests without a matching referrer;
- a security plugin blocking direct access to
/wp-content/uploads/; .htaccessrules in the uploads folder added by a security tool.
If the 403 comes from a CDN, purge that path and confirm the origin serves the file first.
Case 3: the image URL works, but the page shows nothing
Now the file is fine and the page is at fault.
- Open the browser console. A JavaScript error in a lazy-loading or gallery script leaves placeholders in place forever.
- Disable lazy loading in your performance plugin and reload with the cache purged. Aggressive lazy loading combined with a theme's own implementation is a common conflict.
- Check whether the
<img>tag has a realsrc. If it only hasdata-src, the lazy loader failed to run. - Look for a Content Security Policy header blocking the image host. The console names the blocked URL.
- Purge every cache layer — plugin, host and CDN — then test in a private window. See when WordPress changes are not showing for the full purge order.
Case 4: media library thumbnails are missing
The library shows grey boxes but the full-size files exist. WordPress serves the library from generated sizes, and those are lost when a migration copies only original files, or when an image was uploaded while the server was out of memory.
Regenerate them with WP-CLI:
wp media regenerate --yes
Without SSH, a thumbnail regeneration plugin does the same thing. Large libraries can take a long time, so run it during quiet hours and make sure PHP has enough memory — see how to increase the WordPress memory limit if the process dies part way.
Case 5: uploads fail with an HTTP error
If new images will not upload at all, the cause is usually server-side rather than the library:
- PHP memory exhausted while resizing a large image;
upload_max_filesizeorpost_max_sizesmaller than the file;- ImageMagick or GD missing or misconfigured;
- a mod_security rule at the host blocking the upload request.
Test with a small JPEG. If a 200 KB file uploads and a 6 MB file fails, it is a limit, not a permissions problem.
Prevent it happening again
- Back up
wp-content/uploadsas well as the database — see how to back up a WordPress site. - After any move, run search-and-replace with a serialisation-aware tool, then spot-check ten posts.
- Keep original files. Once the originals are gone, regeneration cannot rebuild anything.
- Compress images before upload rather than relying on the server to resize enormous camera files — the details are in how to fix blurry images in WordPress.
Frequently asked
- The editor often serves images through the admin session or a cached preview. A public request may hit a different URL, a CDN that has not fetched the file, or a hotlink protection rule that blocks it.
- Usually not. The original file is normally intact and only the generated sizes are missing, which a thumbnail regeneration tool rebuilds.
- No. Run a search-and-replace on the database to change stored http:// URLs to https://, and serve the files over HTTPS. Re-uploading is never the right fix for a URL problem.