我正在努力维护其他人开发的一些页面。我注意到,表单是由某种图像CAPTCHA保护的,每次用户进入页面时都会生成该图像。 CAPTCHA存储在名为check
的隐藏输入中,用户输入的值与提交表单后隐藏输入的值进行比较。
我尝试使用cURL从隐藏的输入中读取页面和parse CAPTHA。
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, "http://example.com/form/");
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
$result = curl_exec($curl);
$html = str_get_html($result);
$captcha = $html->find('input[name=check]');
var_dump($captcha[0]->value);
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, array(
"name" => "Joe",
"telephone" => "1423456789",
"message" => "Lorem ipsum",
"auth" => $captcha[0]->value,
"check" => $captcha[0]->value,
"submit_f1" => "Send"
));
$result = curl_exec($curl);
curl_close ($curl);
在上面运行脚本会导致正确的表单提交。更重要的是,我注意到,我只能在post数组中覆盖auth
和check
值:
"auth" => 123,
"check" => 123,
并且表单也正确提交。
我意识到没有100%安全的方法来保护表单,但是如何更多地保护我的表单并使自动提交更加困难。
答案 0 :(得分:1)
任何挑战 - 响应系统背后的想法是你保持隐藏的响应(代码),只显示挑战(图像)。
您通常会使用会话来完成此任务;您将响应存储在会话中并显示挑战。输入正确的响应后,您可以清除响应会话变量,为下一次挑战准备系统。
以下代码仅用于说明这一想法。
session_start();
// generate the string you wish to show as captcha
$str = generate_captcha();
// and store inside session
$_SESSION['captcha'] = $str;
// show_captcha() would generate the image
echo show_captcha($str);
session_start();
if ($_POST['captcha'] === $_SESSION['captcha']) {
unset($_SESSION['captcha']);
// continue with form submission
} else {
// yikes, it doesn't match
}
答案 1 :(得分:1)
正如其他人所说,使用$_SESSION
是实现这一目标的最常用方法;
$_SESSION
。但是,如果您无法使用会话,则另一种(稍微不那么常见)的方法是使用哈希;
$ranstr
SHA256($ranstr . $SECRET)
,其中$SECRET
是一个长期服务器端密码值,您应该偶尔更改。$ranstr
绘制到jpg并将其保存在tmp文件夹中。SHA256($POST['human_test'] . $SECRET)
并将其与隐藏字段的值进行比较。在这两种情况下,添加一个cron来删除超过1小时左右的jpgs是个好主意。