BOT対策

This commit is contained in:
2025-12-12 19:40:02 +09:00
parent 6d6fa82fcf
commit 47cf4f9f54
4 changed files with 84 additions and 7 deletions

View File

@@ -20,6 +20,7 @@ class User {
$doLogin = $_SERVER['REQUEST_METHOD'] === 'POST'; $doLogin = $_SERVER['REQUEST_METHOD'] === 'POST';
$error = ''; $error = '';
$nyuU = '';
if ($doLogin) { if ($doLogin) {
if (!\verify_csrf_token($_POST['csrf_token'])) { if (!\verify_csrf_token($_POST['csrf_token'])) {
@@ -29,13 +30,21 @@ class User {
unset($_POST['csrf_token']); unset($_POST['csrf_token']);
$a = []; $a = [];
if (count($_POST) === 2) { $isBot = false;
if (count($_POST) === 4) {
$i = 0; $i = 0;
foreach ($_POST as $p) { foreach ($_POST as $p) {
$a[(int)$i] = $p; $a[(int)$i] = $p;
if ($i >= 2 && $p != '') $isBot = true;
$i++; $i++;
} }
} }
if ($isBot) {
header('Location: /');
exit();
}
$auth = new Auth($a[0]); $auth = new Auth($a[0]);
$res = $auth->isUserExist($a[0]); $res = $auth->isUserExist($a[0]);
if (!$res->isSuccess) { if (!$res->isSuccess) {
@@ -43,6 +52,7 @@ class User {
} else { } else {
$result = $auth->setToken($a[0], $a[1]); $result = $auth->setToken($a[0], $a[1]);
if (!$result->isSuccess) { if (!$result->isSuccess) {
$nyuU = $a[0];
$error = $result->message; $error = $result->message;
} else { } else {
header('Location: /'); header('Location: /');
@@ -60,6 +70,7 @@ class User {
$tmpl->assign('menu', $this->getMenu()); $tmpl->assign('menu', $this->getMenu());
$tmpl->assign('description', $description); $tmpl->assign('description', $description);
$tmpl->assign('error', $error); $tmpl->assign('error', $error);
$tmpl->assign('nyuU', $nyuU);
$tmpl->render('login'); $tmpl->render('login');
} catch (\Exception $e) { } catch (\Exception $e) {
@@ -108,14 +119,21 @@ class User {
unset($_POST['csrf_token']); unset($_POST['csrf_token']);
$a = []; $a = [];
if (count($_POST) === 4) { $isBot = false;
if (count($_POST) === 8) {
$i = 0; $i = 0;
foreach ($_POST as $p) { foreach ($_POST as $p) {
$a[(int)$i] = $p; $a[(int)$i] = $p;
if ($i >= 4 && $p != '') $isBot = true;
$i++; $i++;
} }
} }
if ($isBot) {
header('Location: /');
exit();
}
$auth = new Auth; $auth = new Auth;
$res = $auth->mkUser($a[0], $a[1], $a[2], $a[3]); $res = $auth->mkUser($a[0], $a[1], $a[2], $a[3]);
if (!$res->isSuccess) { if (!$res->isSuccess) {

View File

@@ -44,6 +44,46 @@ function kys(mixed $arg): void {
die(); die();
} }
function ffs(): void {
echo '<style>html { color: #fcfcfc; background-color: #232023; } body { margin: 0; }</style>';
echo '<header style="padding: 10px 0; display: flex; justify-content: space-evenly; background-color: #b61729; margin-bottom: 20px; position: sticky; top: 0;"><div><b>F</b>OR</div> <div><b>F</b>UCKS</div> <div><b>S</b>AKE</div></header>';
$stack = debug_backtrace(DEBUG_BACKTRACE_PROVIDE_OBJECT, 50);
$st = [];
unset($stack[0]);
$i = 0;
echo '<pre>';
print_r($stack);
echo '<pre>';
foreach ($stack as $s) {
if (isset($s['file'])) $st[$i]['file'] = $s['file'].(isset($s['line']) ? ':'.$s['line'] : '');
else $st[$i]['file'] = '';
if (isset($s['function'])) $st[$i]['func'] = (isset($s['class']) ? $s['class'].(isset($s['type']) ? $s['type'] : '::') : '').$s['function'];
else $st[$i]['func'] = '';
if (isset($s['object'])) $st[$i]['objs'] = $s['object'];
else $st[$i]['objs'] = new \stdClass;
if (isset($s['args'])) $st[$i]['args'] = $s['args'];
else $st[$i]['args'] = [];
$i++;
}
unset($stack[$i]);
foreach ($st as $s) {
echo '<div>';
echo '<b>ファイル:</b>';
echo $s['file'].'<br />';
echo '<b>関数:</b>';
echo $s['func'].'<br />';
echo '<b>オブジェクト:</b>';
echo print_r($s['objs']).'<br />';
echo '<b>その他:</b>';
echo print_r($s['args']).'<br />';
echo '</div>';
}
die();
}
function base58btc_encode(string $bin): string { function base58btc_encode(string $bin): string {
$a = '123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz'; $a = '123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz';
$base = 58; $base = 58;
@@ -113,8 +153,7 @@ function to_money($amount, $lang) {
} }
function randstr(): string { function randstr(): string {
srand((int)floor(time() / (60*60*24))); $len = random_int(1, 20);
$len = rand(1, 20);
return bin2hex(random_bytes($len)); return bin2hex(random_bytes($len));
} }
@@ -178,7 +217,7 @@ if (AUTH_ENABLED) {
} }
function verify_csrf_token(string $token): bool { function verify_csrf_token(string $token): bool {
return hash_equals(getcookie('csrf_token'), $token); return null !== getcookie('csrf_token') && hash_equals(getcookie('csrf_token'), $token);
} }
} }

View File

@@ -16,19 +16,27 @@
<form action="/login" method="POST"> <form action="/login" method="POST">
{$ $username = randstr() $} {$ $username = randstr() $}
{$ $password = randstr() $} {$ $password = randstr() $}
{$ $botUsername = randstr() $}
{$ $botPassword = randstr() $}
<table> <table>
<tbody> <tbody>
<tr> <tr>
<td><label for="{{ $username }}">ユーザー名:</label></td> <td><label for="{{ $username }}">ユーザー名:</label></td>
<td><input type="text" id="{{ $username }}" name="{{ $username }}" /></td> <td><input type="text" id="{{ $username }}" name="{{ $username }}" value="{{ $nyuU }}" /></td>
</tr> </tr>
<tr> <tr>
<td><label for="{{ $password }}">パスワード:</label></td> <td><label for="{{ $password }}">パスワード:</label></td>
<td><input type="password" id="{{ $password }}" name="{{ $password }}" /></td> <td><input type="password" id="{{ $password }}" name="{{ $password }}" value="" /></td>
</tr> </tr>
<tr> <tr>
<td></td> <td></td>
<td> <td>
<div style="position:absolute; left:-9999px;">
<input type="text" id="{{ $username }}" name="{{ $botUsername }} value="" />
<input type="password" id="{{ $password }}" name="{{ $botPassword }}" value="" />
</div>
<a href="/?bot=1" style="display:none"></a>
<input type="hidden" id="csrf_token" name="csrf_token" value="{{ make_csrf_token() }}" /> <input type="hidden" id="csrf_token" name="csrf_token" value="{{ make_csrf_token() }}" />
<button>サインイン</button> <button>サインイン</button>
</td> </td>

View File

@@ -18,6 +18,10 @@
{$ $password = randstr() $} {$ $password = randstr() $}
{$ $passwordVerify = randstr() $} {$ $passwordVerify = randstr() $}
{$ $email = randstr() $} {$ $email = randstr() $}
{$ $botUsername = randstr() $}
{$ $botPassword = randstr() $}
{$ $botPasswordVerify = randstr() $}
{$ $botEmail = randstr() $}
<table> <table>
<tbody> <tbody>
<tr> <tr>
@@ -39,6 +43,14 @@
<tr> <tr>
<td></td> <td></td>
<td> <td>
<div style="position:absolute; left:-9999px;">
<input type="text" id="{{ $botUsername }}" name="{{ $botUsername }} value="" />
<input type="password" id="{{ $botPassword }}" name="{{ $botPassword }}" value="" />
<input type="password" id="{{ $botPasswordVerify }}" name="{{ $botPasswordVerify }}" />
<input type="email" id="{{ $botEmail }}" name="{{ $botEmail }}" value="" />
</div>
<a href="/?bot=1" style="display:none"></a>
<input type="hidden" id="csrf_token" name="csrf_token" value="{{ make_csrf_token() }}" /> <input type="hidden" id="csrf_token" name="csrf_token" value="{{ make_csrf_token() }}" />
<button>登録</button> <button>登録</button>
</td> </td>