WordPress后台被暴力撞库告警:登录限速与日志加固

    发布时间:2026-09-26 05:01 更新时间:2026-09-26 05:01 阅读量:1

    不少站长第一次看到后台登录告警,是因为站点装了安全插件,或者干脆是服务器发来一堆 404 与 POST /wp-login.php 的异常记录。这些请求大多来自自动脚本:拿一份常见用户名密码字典,对着 wp-login.php 或 xmlrpc.php 反复提交。它们不一定能撞开,但会消耗 PHP 进程、写满日志,运气不好还会把负载拉高。下面这套做法只针对自己站点的入口做限制与记录,不改动 WordPress 核心逻辑,新手也能照着落地。

    先看清是谁在敲门:登录失败日志在哪

    动手限制之前,先确认攻击来源和频率,否则容易误封正常用户。WordPress 本身不会单独写一份登录失败日志,需要从几个地方拼出全貌。

    一是 Web 服务器访问日志。宝塔面板站点日志一般在 /www/wwwlogs/ 下,按域名命名。用 grep 过滤登录接口,能直接看到请求来源和状态码:

    # 统计最近登录接口的请求来源 TOP 20
    awk '{print $1}' /www/wwwlogs/example.com.log | sort | uniq -c | sort -rn | head -20
    
    

    只看 POST 到 wp-login.php 的请求

    awk '$6 ~ /POST/ && $7 ~ /wp-login.php/ {print $1, $4, $7, $9}' /www/wwwlogs/example.com.log | tail -50

    二是 WordPress 插件。像 Limit Login Attempts Reloaded、Wordfence 这类插件会在数据库里记录失败次数和来源 IP,后台界面比翻日志直观。装哪个看习惯,但注意插件本身也会写表,小站长期用要留意 wp_options 膨胀。

    三是服务器层面的 fail2ban 日志,位置通常是 /var/log/fail2ban.log,前提是你已经配了对应 jail。三种来源对照着看,能区分「偶发输错密码」和「持续撞库」:前者来源 IP 分散、次数个位数,后者往往同一 IP 短时间几十上百次。

    Nginx 层限速:把高频请求挡在 PHP 之前

    最省资源的做法是在 Nginx 层限制登录接口的请求频率。思路很简单:对 wp-login.php 单独开一个限速区,超过阈值直接返回 429,请求根本进不到 PHP,也就不会占用 PHP-FPM 进程。

    在 http 块中定义限速区,然后在站点配置的 server 块里对登录路径引用它。宝塔面板可在「网站 → 设置 → 配置文件」中修改,改完记得重载 Nginx:

    # http 块内:定义名为 wp_login 的限速区,10MB 内存,每秒 3 个请求
    limit_req_zone $binary_remote_addr zone=wp_login:10m rate=3r/s;
    
    

    server 块内:对登录接口限速,突发 5 个请求,超出返回 429

    location = /wp-login.php { limit_req zone=wp_login burst=5 nodelay; limit_req_status 429; include fastcgi.conf; fastcgi_pass unix:/tmp/php-cgi-74.sock; }

    xmlrpc.php 若不用可整体拒绝,减少被撞接口

    location = /xmlrpc.php { deny all; }

    几点避坑:rate 不能设得太死,3r/s 对真人登录足够,但如果你在后台频繁操作、或者公司出口 IP 所有人共用一个地址,可能触发误伤,可以先设 5r/s 观察。fastcgi_pass 的 socket 路径与 PHP 版本相关,以你服务器实际配置为准。另外限速只针对单 IP,分布式撞库效果有限,它解决的是「单点高频」这个最常见场景。

    fail2ban 封禁思路与验证方式

    限速是「减速」,fail2ban 是「拉黑」:读取日志,发现某 IP 在时间窗内失败次数超阈值,就调用防火墙封禁一段时间。它不修改 WordPress,属于服务器侧兜底。

    配置分三部分:filter 定义怎么从日志里认出失败,jail 定义阈值和封禁时长,然后 reload 生效。以访问日志中登录失败返回 200 但带特定标记为例(具体匹配规则要按你日志实际格式调整):

    # /etc/fail2ban/filter.d/wordpress-login.conf 示例片段
    [Definition]
    failregex = ^<HOST> .* "POST /wp-login\.php .*" 200
    ignoreregex =
    
    

    jail.local 中启用

    [wordpress-login] enabled = true filter = wordpress-login logpath = /www/wwwlogs/example.com.log maxretry = 5 findtime = 600 bantime = 3600

    改完执行 fail2ban-client reload,再用 fail2ban-client status wordpress-login 查看当前封禁列表。验证时不要拿自己常用 IP 试,很容易把自己关在门外;可以先调大 findtime、调小 maxretry 做一次演练,确认规则命中后再恢复合理值。注意 fail2ban 依赖系统防火墙,CentOS 系与 Debian 系的防火墙后端不同,配置前先确认 firewalld 或 iptables 处于可用状态,具体以官方文档为准。

    补充两个低成本动作:把默认用户名 admin 改掉、开启强密码;后台地址若不想暴露,可用插件或 Nginx 做一层二次认证。这些和限速、封禁叠加起来,撞库脚本的收益会明显下降。

    小结一下落地顺序:先看日志确认是撞库还是误报,再在 Nginx 给 wp-login.php 加限速,随后按需上 fail2ban 做封禁,最后把登录失败记录纳入日常巡检。做完这一轮,后台告警的噪音会小很多,服务器负载也更稳。下一步可以顺手把 xmlrpc 关闭和后台登录告警通知配上,形成完整的入口防护闭环。

    继续阅读

    📑 📅
    域名下PC站与m站SEO冲突:canonical、自适应与UA跳转取舍 2026-09-26
    宝塔面板升级后网站打不开:PHP扩展、Nginx配置与面板服务逐项回滚排查 2026-09-26
    WordPress中文名附件变乱码或404:编码链路排查 2026-09-26
    CDN与源站双重缓存导致改版不生效:三层缓存刷新顺序 2026-09-26
    Nginx map 指令实战:按 UA、Referer 与域名做条件分流 2026-09-25
    网站301与302混用导致权重分散:跳转类型选择与生效验证 2026-09-27
    宝塔面板部署 WordPress 后固定链接 404:伪静态规则加载顺序与 try_files 排查 2026-09-27
    HTTPS混合内容批量修复:控制台与curl定位http资源 2026-09-27
    MySQL被OOM Kill排查:swap、buffer pool与监控取舍 2026-09-27
    Nginx resolver 域名解析缓存:反代上游换 IP 后仍走旧地址的排查 2026-09-27