共有サーバーの「ログの壁」を突破 | PHPとBashで構築するWordPressリアルタイム監視システム|UNIX Cafe

当サイトでは、コンテンツの一部に広告を掲載しています。
共有サーバーの「ログ不在」を突破 | PHPとBashで構築するWordPressリアルタイム監視システム|UNIX Cafe

UNIX Cafe | 第93回

目次

PHPとBashで構築するWordPressリアルタイム監視システム

WordPressを運営していると、常に不安になるのが「不正アクセス」です。

ある朝、何気なく前日のサーバーログをチェックしていると、そこには、目を疑うような光景が・・・(@@;)

特定の海外IPアドレスから、wp-login.php や xmlrpc.php を執拗に狙った大量の脆弱性スキャナーの跡が、画面を埋め尽くしていたのです。

「これはちょっと放置できん・・・」(・_・、)

この「やられた感」が、今回のプロジェクトのきっかけになりました。「攻撃があったら、その瞬間にメールで知らせてくれる仕組みが欲しい」。そう思い立ち、シェルスクリプトを自作して監視を始めてみたものの、共有サーバー特有の「」にぶつかりました。今回は、その壁をどう乗り越え、自分だけの「お守り」を構築したのか、その記録を共有します。

1. 共有サーバーに立ちはだかる「ログの壁」

最初に作成したのは、サーバーの access_log を1分おきにスキャンするシンプルなBashスクリプトでした。しかし、テストをしても一向にメールが届きません。

原因を調べてみて分かったのは、エックスサーバー(共有プラン)の驚くべき仕様でした。

  • 管理パネルのアクセスログ: システム側で集計された「結果」であり、ファイルではない。
  • サーバー内のログファイル: リアルタイムに更新されず、1日に一度、まとめて書き出される。

つまり、「今この瞬間のアクセスログ」は、ユーザーが触れる場所には存在しないのです。これではリアルタイムの監視は不可能です。

2. UNIX流の解決策:無ければ作る「自作リアルタイムログ」

ここで諦めないのがUNIX流の考え方です。「サーバーがログをくれないなら、自分でログを吐き出す仕組みを作ればいい」という発想に切り替えます。

幸い、WordPressには必ず index.php という玄関口があります。ここに数行のPHPコードを仕込み、自分専用の「生きたログ」を生成することにしました。

index.php への追記(玄関にメモ帳を置く)

/public_html/index.php の先頭に以下のコードを追加します。

Xserver 用のPHPファイルです。ログファイルのパスは、お使いの環境によって異なります。

xs123456(サーバーID)や pc-fan.net(ドメイン名)は、ご自分の環境に合わせて書き換えてください。

  • サーバーIDの調べ方: 「エックスサーバーの管理パネルの一番上に表示されているIDです」
  • フルパスの調べ方: 「/home/サーバーID/ドメイン名/... という形になります」

// --- リアルタイムログ出力設定 ---
//サーバーIDとドメイン名をご自身のものに書き換えてください
$log_file = '/home/xs123456/pc-fan.net/script/my_access.log';
$log_data = sprintf(
    "[%s] %s %s %s\n",
    date('d/M/Y:H:i:s O'),
    $_SERVER['REMOTE_ADDR'],
    $_SERVER['REQUEST_METHOD'],
    $_SERVER['REQUEST_URI']
);
file_put_contents($log_file, $log_data, FILE_APPEND | LOCK_EX);
// -----------------------------

これで、誰かがサイトを訪れた瞬間に my_access.log へ足跡が刻まれるようになりました。

3. 門番となる監視スクリプトの設計

次に、この自作ログを監視するスクリプト scan_log.sh を作成します。ここで重要なのが、「しおり(ステート管理)」の概念です。

しおりを上手に使って二重通知を回避しないと、大量の通知が届いてメールボックスがパンクしてしまいます。そこで、last_line.txt というファイルに「前回何行目まで読んだか」を記録し、常に続きからスキャンする仕組みを導入します。

scan_log.sh のエッセンス

サーバーに設置するBashスクリプト

こちらでも同様に、パス内のサーバーID等の書き換えが必要です。

#!/bin/bash

# =================================================================
# UNIX Cafe ログ防衛システム (scan_log.sh)
# 役割: ログの新しい行だけをチェックし、攻撃を検知したらメール通知する
# =================================================================

# --- 設定エリア ---
# 1. サーバーIDとドメイン名をご自身のものに書き換えてください
LOG_FILE="/home/xs123456/pc-fan.net/log/access_log"

# 2. 状態保存ファイル(どこまで読んだか記録するしおり)
STATE_FILE="/home/xs123456/pc-fan.net/script/last_line.txt"

# 3. 通知先メールアドレスを書き換えてください
MAIL_TO="e-mail"

# 4. 検出キーワード(脆弱性スキャンの特徴的なパスやツール名)
PATTERNS="wp-login.php|xmlrpc.php|.env|sqlmap|nikto|acunetix|nessus"

# --- 処理開始 ---

# ログファイルが存在しない場合は、エラーを出さず終了
if [ ! -f "$LOG_FILE" ]; then
    exit 0
fi

# 前回の最終行を取得(記録がなければ0行目から)
if [ -f "$STATE_FILE" ]; then
    LAST_LINE=$(cat "$STATE_FILE")
    # 数字以外が入っていた場合の対策
    if ! [[ "$LAST_LINE" =~ ^[0-9]+$ ]]; then LAST_LINE=0; fi
else
    LAST_LINE=0
fi

# 現在のログの総行数を取得
CURRENT_TOTAL_LINES=$(wc -l < "$LOG_FILE")

# ログがリセット(回転)されていたら、最初から読み直す
if [ "$CURRENT_TOTAL_LINES" -lt "$LAST_LINE" ]; then
    LAST_LINE=0
fi

# 新しく増えた行だけを抽出してパターン検索
# tail で「前回読んだ次の行」から最後までを切り出し、grep で検索
NEW_HITS=$(tail -n +$((LAST_LINE + 1)) "$LOG_FILE" | grep -E "$PATTERNS")

# 攻撃が検出された場合のみメールを送信
if [ -n "$NEW_HITS" ]; then
    # メールの本文作成
    BODY=$(echo -e "脆弱性スキャナーと思われるアクセスを検出しました。\n\n【対象ログ】\n$LOG_FILE\n\n【検出内容】\n$NEW_HITS")
    
    # メール送信(件名にはサーバー名を含める)
    echo "$BODY" | mail -s "【重要】脆弱性スキャナ検知通知($(hostname))" "$MAIL_TO"
fi

# 今回読んだ最後の行数を保存(次回の開始位置にする)
echo "$CURRENT_TOTAL_LINES" > "$STATE_FILE"

exit 0

4. SSHとCronによる「24時間自動監視」

SSHでサーバーにログインし、パーミッションを調整(chmod 700)という数字を指定することで、所有者であるあなただけが実行・読み書きできるようになり、安全に動作させることができます。

実行コマンド:

chmod 700 /home/xs123456/pc-fan.net/script/scan_log.sh

※作成したスクリプトを『プログラム』として動かすための設定です。自分だけが実行できるように権限を絞ります。

エックスサーバーのCron設定から設定を追加

  • 実行間隔: 15分(通知の嵐を防ぎつつ、実用的な頻度)
  • メンテナンス: 毎週日曜にログをリセット

不正アクセス監視(wp-login等への攻撃を検知してメール通知)

/bin/bash /home/xs123456/pc-fan.net/script/scan_log.sh > /dev/null 2>&1 
Cron設定一覧Cron追加設定
15
時間*
*
*
曜日*
コマンド/bin/bash /home/xs744164/pc-fan.net/script/scan_log.sh > /dev/null 2>&1
メモ不正アクセス監視(wp-login等への攻撃を検知してメール通知)

ログお掃除:毎週日曜に監視用ログを空にする

# ログ掃除としおりリセットのセット
cp /dev/null my_access.log && echo 0 > last_line.txt
Cron設定一覧Cron追加設定
*
時間3
*
*
曜日0
コマンドcp /dev/null /home/xs744164/pc-fan.net/script/my_access.log && echo 0 > /home/xs744164/pc-fan.net/script/last_line.txt
メモログお掃除:毎週日曜に監視用ログを空にする

特に毎週の「お掃除コマンド」は重要です。ログを空にすると同時に、しおりも「0」に戻すセット処理をCronに仕込みました。

まとめ:自分だけの「お守り」を育てる

SSHでの操作やスクリプトの自作に挑んだことで、以前はブラックボックスだったサーバーの裏側が、手に取るように理解できるようになりました。

そんな時、サーバーから一通のメールが届きました。 「脆弱性スキャナーと思われるアクセスを検出しました」 ログを確認すると、/wp-login.php への不審なアクセスが正確に捉えられていました。

苦労して書き上げたスクリプトが、現実に自分のサイトを守ってくれている実感が湧き、深い安心感を覚えました。シンプルな道具を組み合わせ、仕組みを読み解きながら構築していく。この試行錯誤のプロセスこそが、まさに『UNIXの思想』そのものであると強く実感しています。」

さらに学びたいあなたへ

📘 用途ごとに選ぶ Linux のおすすめ本

よかったらシェアしてね!
  • URLをコピーしました!
  • URLをコピーしました!

この記事を書いた人

のいのアバター のい UNIX Cafe 編集部

UNIX Cafe は、むずかしい言葉をできるだけ使わず、物語を読むような気持ちで気軽に学べる場所です。
プログラミングは、アイデアをコンピューターに伝えるための「ことば」。
簡単な単語と文法を覚えることで、誰でもターミナルから便利なコマンドを使えるようになります。
コーヒーを片手に立ち寄るような気持ちで、やさしいプログラミングの世界を、
そっとのぞいてみてください。

目次