* 同一spamを投稿されにくくする工夫 [#i5ea33e9] - ページ: [[BugTrack2]] - 投稿者: [[teanan]] - 優先順位: 普通 - 状態: 提案 - カテゴリー: プラグイン - 投稿日: 2007-10-06 (土) 11:13:23 - バージョン: ** メッセージ [#jcf07afd] 同じ内容のコメントspamをたくさんのページに投稿される場合があります。現状のcommentプラグインは無防備ですので、spam投稿のコスト(投稿者の手間)を少しでも高くするための工夫を施しましょう。 ** パッチ [#x0d1fc85] PukiWiki-1.4.7_notb(comment.inc.php v1.36)からの差分です。 --- comment.inc.php.orig Sat Jan 28 23:54:51 2006 +++ comment.inc.php Sat Oct 06 10:48:42 2007 @@ -18,6 +18,8 @@ define('PLUGIN_COMMENT_FORMAT_NOW', '&new{$now};'); define('PLUGIN_COMMENT_FORMAT_STRING', "\x08MSG\x08 -- \x08NAME\x08 \x08NOW\x08"); +define('PLUGIN_COMMENT_MIXTURE', 'comment_mixture'); + function plugin_comment_action() { global $script, $vars, $now, $_title_updated, $_no_name; @@ -51,9 +53,11 @@ $postdata = ''; $comment_no = 0; $above = (isset($vars['above']) && $vars['above'] == '1'); + $hash = isset($vars['hash'])? $vars['hash'] : ''; foreach (get_source($vars['refer']) as $line) { if (! $above) $postdata .= $line; - if (preg_match('/^#comment/i', $line) && $comment_no++ == $vars['comment_no']) { + $check = plugin_comment_gethash($vars['refer'], $comment_no); + if (preg_match('/^#comment/i', $line) && $comment_no++ == $vars['comment_no'] && $hash === $check) { if ($above) { $postdata = rtrim($postdata) . "\n" . $comment . "\n" . @@ -93,6 +97,7 @@ if (! isset($numbers[$vars['page']])) $numbers[$vars['page']] = 0; $comment_no = $numbers[$vars['page']]++; + $hash = plugin_comment_gethash($vars['page'], $comment_no); $options = func_num_args() ? func_get_args() : array(); if (in_array('noname', $options)) { @@ -118,6 +123,7 @@ <input type="hidden" name="plugin" value="comment" /> <input type="hidden" name="refer" value="$s_page" /> <input type="hidden" name="comment_no" value="$comment_no" /> + <input type="hidden" name="hash" value="$hash" /> <input type="hidden" name="nodate" value="$nodate" /> <input type="hidden" name="above" value="$above" /> <input type="hidden" name="digest" value="$digest" /> @@ -130,4 +136,12 @@ return $string; } + +function plugin_comment_gethash($page, $comment_no) +{ + global $page_title; + return md5($page_title . $page . $comment_no . $_SERVER['REMOTE_ADDR'] . + PLUGIN_COMMENT_MIXTURE); +} + ?> ** 仕組み [#q86e5046] - commentプラグインによる入力フォームを表示する際、"hash"にページ名やREMOTE_ADDR等から導き出す md5 のハッシュ値を指定します。 - コメントが投稿された場合、指定されたhashが正しいものかをチェックします。不一致であれば、コメント挿入の処理を行いません。 ** ポイント [#w8cb7ea9] - spam発信者が同一雛型を使って、複数ページへ投稿することをブロックする -- 発信者が複数ページへ投稿するためには、全てのコメントフォームごとに異なった hash を指定する必要があります。 -- hash は REMOTE_ADDR を含んでいるため、IPを切り替えて投稿してくるようなspam発信者は、その度に hash を更新する必要があります。 - spamが投稿されるようになった場合、簡単に対処したい -- hash の生成には、commentプラグインで共通の混ぜ物('PLUGIN_COMMENT_MIXTURE')を入れてありますので、spamが来るようになった場合、この定義を変更するだけで対処することができます。 -------- - お疲れ様です。戦略も付記いただきたいのですが、これはあらかじめ comment form を与える過程でクライアントに "クライアントごとの REMOTE_ADDR と、サイトの秘密の文字列などから生成した hash" を渡しておいて、それを含んだ HTTP POST のみ許可する といったものでしょうか。異なるIPから渡してきたり、複数のIPから渡してくる奇妙なPOSTはブロックされます。また hash はページ名も含んでいるので、異なるページから生成したひな型もブロックされます。 -- [[henoheno]] &new{2007-10-06 (土) 21:41:18}; -- 戦略上の欠点として、事前に REMOTE_ADDR ごとに異なる内容の通常コンテンツを与えておく必要があります。これがproxyサーバーのキャッシュを汚してしまうので、(HTTPで)proxyサーバーにコンテンツを覚えないよう伝える必要があるでしょう。 -- [[henoheno]] &new{2007-10-06 (土) 21:46:07}; -- なお、MD5 hash は数字列になりうるので、$hash === $check として型も区別させないと、意図に反して true を返す可能性が生じますです (See [[BugTrack2/236]]) -- [[henoheno]] &new{2007-10-06 (土) 21:47:27}; --- ご指摘のとおりです、ありがとうございます。パッチ修正しておきます (^^; -- [[teanan]] &new{2007-10-06 (土) 22:07:28}; -- 説明不足で申し訳ありません。簡単ですが、仕組みとポイントを列挙いたしました。Proxyが効かなくなるのも、問題になるかもしれませんね… -- [[teanan]] &new{2007-10-06 (土) 22:28:40}; -- いえこちらの反応が早すぎたのでしょう (^^; -- [[henoheno]] &new{2007-10-06 (土) 23:39:22}; - Proxyサーバーについては、REMOTE_ADDRがProxyサーバーのアドレスになるため、問題ないような気がします。 -- [[teanan]] &new{2007-10-07 (日) 11:39:36}; -- うほ、そうかもしれない。このhashに何を含めるかで色々条件が変わりますね XD -- [[henoheno]] &new{2007-10-07 (日) 22:16:57}; - 汎用化: この件、comment番号にこだわらなければ、commentプラグインに限らないあらゆるformに(強制挿入することで)適用できる気がします。強制挿入については、現在の手法が好ましいとは思いませんが既に encode_hint がやっています。そうした汎用hashのチェックはプラグインに渡る前に処理できます -- [[henoheno]] &new{2007-10-07 (日) 23:15:54}; -- 特化: プラグインごとにさらに厳しくチェックしたい場合、そうしたhashを関数で取得できるようにしておいて、各プラグインが独自に comment 番号などをmixした別のhashを生成する形にすれば両立できそうです -- [[henoheno]] &new{2007-10-07 (日) 23:18:05}; #comment