passend zur Diskussion über DNS Blacklist Checks habe ich ein kleines Modul geschrieben, was beim Betreten einer Webseite die IP-Adresse des Besuchers mit einer DNS-Blackliste abgleicht und gegebenenfalls den Zugang zur Seite verweigert.
Hier die Modul-Ausgabe:
Code: Alles auswählen
<?php
if (!($edit || $contenido)) {
cInclude("classes", "contenido/class.client.php");
cInclude("classes", "class.user.php");
$cApiClient = new cApiClient($client);
$clientAdmins = User::getClientAdmins($client);
$cfg["tab"]["spamcache"] = $cfg['sql']['sqlprefix'] . "_spamcache";
$sql = "CREATE TABLE IF NOT EXISTS `" . $cfg["tab"]["spamcache"] . "` (`ip` VARCHAR(15) NOT NULL, `dnsbl` TINYTEXT NOT NULL DEFAULT '', `lastaccessed` TIMESTAMP ON UPDATE CURRENT_TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, PRIMARY KEY (`ip`))";
$db->query($sql);
$sql = "DELETE FROM `" . $cfg["tab"]["spamcache"] . "` WHERE ROUND((NOW() - `lastaccessed`) / 60) >= 5";
$db->query($sql);
$sql = "SELECT * FROM `" . $cfg["tab"]["spamcache"] . "` WHERE `ip`='$_SERVER[REMOTE_ADDR]'";
$db->query($sql);
if ($db->next_record()) {
$dnsbl = $db->f('dnsbl');
$sql = "UPDATE `" . $cfg["tab"]["spamcache"] . "` SET `lastaccessed`=NOW() WHERE `ip`='$_SERVER[REMOTE_ADDR]'";
$db->query($sql);
if ($dnsbl)
dieSpammer($dnsbl);
} else {
$dnsbls = explode(",", $cApiClient->getProperty("dnsbls", "servers"));
if (is_array($dnsbls)) foreach ($dnsbls as $dnsbl) {
$prefix = $cApiClient->getProperty("dnsbls", $dnsbl);
if ($prefix) $prefix = ".$prefix";
if ($dnsbl && isSpammer("$_SERVER[REMOTE_ADDR]$prefix", $dnsbl)) {
$sql = "INSERT INTO `" . $cfg["tab"]["spamcache"] . "`(`ip`, `dnsbl`) VALUES('$_SERVER[REMOTE_ADDR]', '$dnsbl')";
$db->query($sql);
dieSpammer($dnsbl);
}
}
$sql = "INSERT INTO `" . $cfg["tab"]["spamcache"] . "`(`ip`) VALUES('$_SERVER[REMOTE_ADDR]')";
$db->query($sql);
}
}
function isSpammer($ip, $dnsbl) {
if (!function_exists("gethostbyname"))
return false;
if (!preg_match('/(?:(?:[1-9]|[1-9][0-9]|1[0-9]{2,2}|2[0-4][0-9]|25[0-5])\.){4,4}/', "$ip."))
return false;
$hostname = join(".", array_reverse(explode(".", $ip))) . ".$dnsbl";
return gethostbyname($hostname) != $hostname;
}
function dieSpammer($dnsbl) {
global $clientAdmins;
header("HTTP/1.0 403 Forbidden");
header("Content-type: text/plain");
if (is_array($clientAdmins))
$admin = array_shift($clientAdmins);
die(sprintf("Sorry!\n\n%s says you are a spammer and we don't want spammers to use our services!\n" . (@$admin["email"] ? sprintf("If you think this is incorrect, please drop us a line via email to: %s.\n", str_replace("@", "(AT)", $admin["email"])) : '') . "\nThanks a lot.", $dnsbl));
}
?>
Typ: dnsbls
Name: servers
Wert: <Komma-getrennte Liste von Servern>
Project Honey Pot beispielsweise braucht noch einen Zugangsschlüssel, solche Schlüssel können als
Typ: dnsbls
Name: <Hostname des Servers wie in der Liste>
Wert: Zugangsschlüssel
hinterlegt werden. Das Abfrageergebnis wird in der Datenbank zwischengespeichert und nach 5 minütiger Inaktivität des Besuchers
wieder entfernt.
Nachtrag: Das Modul muss als erstes im Layout der Seite geladen werden, also noch vor der Dokumenttypdeklaration, da die Ausgabe der Seite im Falle eines Spammers abgebrochen - und ein HTTP 403-Header gesendet wird.