IP アドレスでアクセスを禁止している spammer が,その後どれだけアクセスを続けているかをカウントする php コードを,今回は MySQL を使って実装した.
まず最初に注意点. ErrorDocument 403 で php ファイルへ飛ばす場合,その php ファイルへのアクセスは可能とすること.
さもなくば, 403 の転送で無限ループが発生する.
具体的には,.htaccess へ下記を追記.hogehoge.phpの部分は,設置したphpファイル名に変更すること.
<Files hogehoge.php> allow from all </Files>
spammer のアクセスが集中している時など,どうしても
spammer counter v2
では,ファイル書き込みに失敗するようだ.
その結果,度々ファイルがクリアされてしまっていた.
んで,よく考えたらこのサイトでは MySQL を使う blog が2つも動いていることを思い出したので,
DB で実装することにした.
とても楽チン.
そのコードは,こんな感じ.
<?php header('HTTP/1.1 403 Forbidden'); header('Content-Type: text/html; charset=iso-8859-1'); ?> <!DOCTYPE HTML PUBLIC '-//IETF//DTD HTML 2.0//EN'> <HTML><HEAD> <TITLE>403 Forbidden</TITLE> </HEAD><BODY> <H1>Forbidden</H1> <?php printf('You don't have permission to access %s\non this server.', htmlentities(strip_tags($_SERVER['REQUEST_URI']))); ?><P> <HR> <ADDRESS><?php $e = explode(' ',$_SERVER['SERVER_SOFTWARE']); printf('%s Server at %s Port %d',$e[0],$_ENV['SERVER_NAME'],$_ENV['SERVER_PORT']); ?></ADDRESS> </BODY></HTML> <?php // MySQL $mySqlHost = 'xxx.xxx.xxx'; $dbname = 'database_name'; $user = 'user_name'; $password = 'password'; $table = 'spammer_counter'; // connecting $mobj = mysql_connect($mySqlHost,$user,$password); if ($mobj == FALSE) { die('broken');} // count IP addr $addr = $_SERVER['REMOTE_ADDR']; mysql_select_db($dbname,$mobj); $done=mysql_query('insert into '.$table.' (ipaddr,number) values (''.$addr.'',1) ' .'on duplicate key update number=number+1;'); mysql_close($mobj); if ($done == FALSE) { die('no response...');} ?> 欠点は,データを見るのに DB を叩く必要があること. それは嫌なので,viewer も作った. </p> <p class="pre"> <?xml version='1.0' encoding='Shift_JIS'?> <!DOCTYPE html PUBLIC '-//W3C//DTD XHTML 1.0 Transitional//EN' 'http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd'> <html xmlns='http://www.w3.org/1999/xhtml' xml:lang='ja' lang='ja'> <head><title>spammer viewer</title></head> </body> <h1>spammer viewer</h1> <table style='border: black solid 1px;'> <tr><th>IP addr</th><th># of access</th></tr> <?php // MySQL $mySqlHost = 'xxx.xxx.xxx'; $dbname = 'database_name'; $user = 'user_name'; $password = 'password'; $table = 'spammer_counter'; // connecting $mobj = mysql_connect($mySqlHost,$user,$password); if ($mobj == FALSE) { die('broken');} mysql_select_db($dbname,$mobj); $done=mysql_query('select * from '.$table.';'); mysql_close($mobj); if ($done == FALSE) { die('no response...');} while ( $row = mysql_fetch_row($done)) { printf(' <tr><td>%s</td><td style=\'text-align:right;\'>%d</td></tr>\n',$row[0],$row[1]); } ?> </table> </body> </html>