σ(^^)が管理してるMovableTypeサーバー2台が、ときどきハングアップしたように無反応になることが時々ありまして、topによるとmt-tb.cgiが原因ぽい。つまり、トラックバック処理でリソースが食いつぶされているということですね。
spamトラックバックのフィルタリング自体はMT内蔵機能でほぼ解決できるんですが、この処理自体が重すぎて、山のようにトラックバックが来た場合にDoS状態になってしまう訳です。
そこでApacheレベルで特定のリクエストを排除できるmod_securityを導入してみました。1.8/1.9系の設定例はたくさん見つかるんですが、設定文法がまるっと変更された2.x系の情報は見つからず苦労しました。なにも考えずに最新版を導入してしまった…
とりあえず設定してみたって段階ですが、覚え書きしておきます。
■インストール
ウチの環境だと、mod_unique_idは導入済みでした。libxml2はlibxml2-develパッケージまで入れておく必要があるみたいです。
で、後はアーカイブを展開し、Makefile内のtop_dir = 行に、httpd.confのServer rootで指定してあるパスを記入し、make、make installします。
Apache側の設定として、httpd.confの然るべき場所に、
LoadFile /usr/lib/libxml2.so
LoadModule unique_id_module modules/mod_unique_id.so
LoadModule security2_module modules/mod_security2.so
を記入します。
■日本語を含まないトラックバックを弾く
公式サイトには、USER-AGENTやIPアドレスなどのブラックリストを定義した設定ファイルが色々置かれていますが、この手は最新版を入れ続けないと効果が薄そうだし、ルックアップの負荷も大きそうなので、とりあえず日本の皆さんがやられている「日本語(2バイト文字)を含まないものを弾く」というアプローチを採ってみます。
具体的な設定は、同じくhttpd.confで、
<Files “mt-tb.cgi”>
SecRuleEngine On
SecRequestBodyAccess On
SecDefaultAction deny,log,status:406,phase:2,t:urldecode
SecRule REQUEST_BODY “^[\x00-\x7F]+$”
SecAuditEngine On
SecAuditLog /var/log/httpd/mod_security.log
</Files>
としてみました。Filesディレクティブでトラックバック用スクリプトにだけ働くように指定しています。1.x系から変更になったコマンド名だけを書き換えるだけでは上手くいかず試行錯誤したんですが、どうやらSecDefaultActionにt:urlencodeを追加したら上手くいったっぽいです。
動作試験しようにも、ウチのブログはブログ名が日本語なので、 一時的に
SecRule ARGS:excerpt “^[\x00-\x7F]+$”
のように、POSTデータの内、excerpt(トラックバックで送られる概要)のみを検査対象にし、本文に日本語を含むエントリと含まないエントリからトラックバックしてみたところ、一応後者のみが弾かれました。
これでしばらく様子を見てみたいと思います。
が、しかし本ブログに関してはそもそもトラックバックが正しく受信できない問題が発覚しました。別途原因究明しないと…
ともあれ、このmod_securityはかなり柔軟にレシピが書けるので、Webアプリケーションのセキュリティ対策に色々と活用できそうです。