Apache Log 智能封鎖腳本:自動擷取異常存取與黑名單管理(含 ipset 實作)

Category: 技術手記 Tags: apache, access.log, error.log, 自動封鎖, ipset, Linux 防火牆, fail2ban 替代


🕵️ 背景說明

在大量來自海外的機器人、爬蟲與攻擊流量中,我發現除了 TCP SYN Flood 之外,Apache 的 access.log 與 error.log 裡也有大量異常存取行為,例如:

  • 不存在的網址(404)
  • 權限拒絕(403)
  • 掃描漏洞(例如嘗試連到 /wp-login.php, /phpmyadmin 等)

這些都是潛在攻擊前兆,因此我撰寫一份腳本,定期分析 Apache 的 log 檔,自動封鎖惡意 IP。


🔍 腳本偵測規則

支援以下條件:

  • 來自 access.log 或 error.log
  • 出現大量 403 或 404 回應(可自訂次數門檻)
  • 僅掃描 .log 結尾的檔案,跳過 .log.1 或 .gz 歷史檔
  • 可選擇性分析過去 N 分鐘內的 log 記錄(例如搭配 date + awk 過濾)

例如:

grep -hE ' 403 | 404 ' /var/log/apache2/*access.log \
  | awk -v since="$(date --date='5 minutes ago' '+%d/%b/%Y:%H:%M')" \
         '$4 > "["since' {print $1}'

此方法可限制分析最近 5 分鐘內的異常行為,避免封鎖過時的 IP。


✅ 腳本實作邏輯:apache-ban-ip.sh

#!/bin/bash

export PATH=/usr/sbin:/usr/bin:/bin:/sbin
LOG_DIR=/var/log/apache2
IPSET_NAME="blacklist"
THRESHOLD=50
IPSET_TIMEOUT=3600
WHITELIST=("127.0.0.1" "你的管理員IP")

# 初始化 ipset
ipset list $IPSET_NAME >/dev/null 2>&1 || ipset create $IPSET_NAME hash:ip timeout $IPSET_TIMEOUT

is_whitelisted() {
  for wip in "${WHITELIST[@]}"; do
    [[ "$1" == "$wip" ]] && return 0
  done
  return 1
}

# 計算最近 5 分鐘的時間戳格式(Apache log 格式)
SINCE=$(date --date='5 minutes ago' '+%d/%b/%Y:%H:%M')

# 擷取最近 5 分鐘內 access.log 中 403, 404 的來源 IP(僅限 .log 結尾)
grep -hE ' 403 | 404 ' $LOG_DIR/*access.log \
  | awk -v since="$SINCE" '$4 > "["since {print $1}' \
  | sort | uniq -c | sort -nr \
  | awk -v thr=$THRESHOLD '$1 > thr {print $2}' \
  | while read ip; do
    if is_whitelisted "$ip"; then
      echo "[略過] $ip 為白名單"
      continue
    fi
    echo "[封鎖] $ip 超過異常門檻,加入黑名單"
    ipset add $IPSET_NAME $ip timeout $IPSET_TIMEOUT 2>/dev/null
  done

⏰ 建議排程(每 5 分鐘一次)

sudo crontab -e

加入:

*/5 * * * * /usr/local/bin/apache-ban-ip.sh >> /var/log/apache-ban.log 2>&1

📌 補充設定(若未設)

請確保你已有正確的 iptables drop 規則:

sudo iptables -I INPUT -m set --match-set blacklist src -j DROP

📊 後續可進階方向

  • 加入封鎖 IP 通知(LINE Notify / Email)
  • 將每次封鎖記錄存入 SQLite / JSON Log
  • 做出白名單 / 灰名單 / 封鎖名單 dashboard
  • 用 fail2ban 整合也可以,但此腳本更輕量彈性

🧠 結語

這支腳本已幫助我自動防禦數千次非法掃描與惡意請求,等同為 Apache 建立了應用層 WAF 界限。

若你正在經營 WordPress、WooCommerce、或自架 API Gateway,這個腳本將成為你最值得信任的守門員。

開源、自由擴充,安全你自己定義。

Reality Breaker — 拒絕被動,用邏輯穿透風暴。

codeant