Finding out your WordPress site has been hacked is stressful, and the natural reaction is to start deleting suspicious files straight away. That usually makes things worse: you destroy the evidence of how the attacker got in, miss the backdoor they left behind, and the site is reinfected within days.
Cleaning a hacked site works best in a fixed order: contain it, lock the attacker out, find everything they changed, replace rather than repair, and close the hole they came through. This guide walks through each stage.
Signs Your Site Has Been Hacked
- Visitors are redirected to spam, scam, or adult sites, sometimes only on mobile or only when arriving from Google.
- Google shows “This site may be hacked” in search results, or Chrome shows a red “Dangerous site” warning.
- Search results show pages you didn’t create, often in another language or selling pharmaceuticals.
- Administrator accounts you don’t recognize, or plugins you didn’t install.
- Your host suspends the account or reports malware, spam sending, or unusual resource use.
- Unfamiliar code at the top of
wp-config.php,index.php, or theme files.
Some infections only show themselves to logged-out visitors or to search engines, so check the site in a private window and look at what Google shows for site:yourdomain.com.
Stage 1: Contain the Damage
- Tell your host. They can often see which files were changed and when, scan the account at the server level, and may have clean backups you don’t know about.
- Back up the infected site, files and database. It sounds backwards, but if cleanup goes wrong you need something to go back to, and it preserves evidence of how the attack happened. Label it clearly so it’s never restored by mistake.
- Put the site in maintenance mode if it’s redirecting visitors or serving malware, so you stop harming them while you work.
Stage 2: Lock the Attacker Out
Do this early, so the attacker can’t simply log back in while you clean.
- Change every password: all WordPress administrator accounts, your hosting account, SFTP and SSH, and the database user (then update
DB_PASSWORDinwp-config.phpto match). Also change your email account password if it receives password reset links. - Replace the security keys and salts in
wp-config.phpwith a fresh set fromhttps://api.wordpress.org/secret-key/1.1/salt/. This logs out every session, including the attacker’s. - Check for administrator accounts you don’t recognize. Malware sometimes hides its accounts from the Users screen, so check the database directly in phpMyAdmin (adjust
wp_to your table prefix):
SELECT u.ID, u.user_login, u.user_email, u.user_registered
FROM wp_users u
JOIN wp_usermeta m ON m.user_id = u.ID
WHERE m.meta_key = 'wp_capabilities'
AND m.meta_value LIKE '%administrator%';
Delete any administrator you don’t recognize, assigning their content to a real account if WordPress asks.
Stage 3: Find Everything That Was Changed
Run scanners
Use a security plugin’s malware scan (Wordfence’s free scan is thorough) and your host’s scanner if they have one. Scanners won’t catch everything, but they quickly show the obvious infected files and modified core files.
Check WordPress core and plugins against the originals
With WP-CLI, these commands compare your files with the official versions and list anything modified or added:
wp core verify-checksums
wp plugin verify-checksums --all
The plugin check only works for plugins from WordPress.org. Premium plugins need reinstalling from the vendor instead.
Look in the places backdoors usually hide
- PHP files in uploads.
wp-content/uploadsshould only contain media. Any.phpfile there is almost certainly malicious. With SSH,find wp-content/uploads -name "*.php"lists them. - Recently modified files.
find . -type f -name "*.php" -mtime -14lists PHP files changed in the last 14 days. Compare the dates with when the problem started. wp-config.php,.htaccess, andindex.phpin the root, which attackers often modify to load malware or add redirects.wp-content/mu-plugins/, which loads automatically and doesn’t appear in the normal Plugins list, and drop-ins such aswp-content/object-cache.phpthat you didn’t install.- Plugins and themes you don’t remember installing.
Malicious code is often heavily obfuscated, with long unreadable strings combined with functions such as eval(), base64_decode(), gzinflate(), or str_rot13(). Legitimate plugins use some of these too, so they’re a reason to look closer, not proof on their own.
Check the database
- Search posts and pages for injected scripts and hidden spam links: in phpMyAdmin, search the
wp_poststable’spost_contentfor<scriptand for unfamiliar domains. - Check that
siteurlandhomeinwp_optionsstill point to your own domain. - Look for unexpected entries in your hosting panel’s Cron Jobs screen, which attackers use to reinstall malware.
Stage 4: Clean the Site
Replace files rather than trying to repair them. Removing malicious lines one by one is slow, and it’s easy to miss one.
- If you have a clean backup from before the infection, restoring it is often the fastest route. Then go straight to Stage 5, or the same hole will be used again.
- Reinstall WordPress core: from the dashboard with Dashboard → Updates → Re-install, with
wp core download --force, or by uploading freshwp-adminandwp-includesfolders. Never overwritewp-contentorwp-config.phpthis way. - Reinstall every plugin and theme from WordPress.org or the vendor. Delete the old folders first, rather than uploading over them, so no extra files are left behind.
- Delete PHP files in uploads, unknown plugins and themes, and anything you found in Stage 3.
- Clean
wp-config.php,.htaccess, and the database entries you found, comparingwp-config.phpagainstwp-config-sample.phpif you’re unsure what belongs there.
Then scan again, and check the site logged out, on mobile, and by clicking through from a Google search.
Stage 5: Close the Hole
A site cleaned without fixing the original weakness usually gets reinfected. The most common ways in are:
- An outdated plugin or theme with a known vulnerability. Update everything, and delete what you don’t use.
- A “nulled” pirated premium plugin or theme. These very often contain backdoors. Replace them with genuine copies.
- A weak or reused password. Strong passwords and two-factor authentication fix this. See our guide to stopping brute force attacks.
- Another site on the same hosting account. On shared hosting, an infected old site can reinfect every other site in the account. Clean or remove all of them.
- An infected computer used to log in. Run a malware scan on the devices you use for SFTP and admin access.
Then work through our WordPress security checklist, especially blocking PHP in uploads, DISALLOW_FILE_EDIT, and off-site backups.
Stage 6: Recover in Google
If Google flagged your site, open Google Search Console → Security & Manual Actions → Security issues. It lists what Google found, often with example URLs. Once the site is clean and you’ve checked those URLs, click Request review and describe what you fixed. Don’t request a review until you’re confident the site is clean, because a failed review delays the next one.
Spam pages the attacker created may stay in search results for a while. Make sure they now return a 404 or 410 so Google drops them.
When to Get Professional Help
Consider a professional cleanup service, or your host’s security team, if the infection returns after cleaning, the site handles payments or customer data, you can’t find the entry point, or you’re not comfortable working with files and the database. For an online store, a quick, verified cleanup is usually worth the cost.
Summary
Contain first: tell your host, back up the infected site, and stop visitors being harmed. Lock the attacker out with new passwords, new salts, and a check for hidden admins. Find every change with scanners, checksums, and the usual hiding places, then replace core, plugins, and themes instead of repairing them. Finally, close the hole the attacker used, and request a review in Search Console once the site is clean.