如何使用 PHP Curl 库登录网站?
How to login on website with PHP Curl library?
我想使用 PHP CURL 库登录 https 上的页面。重新加载此页面。但我做不到。我无法从服务器或本地主机建立连接。
$username = "pik123@gmail.com";
$password = "Bf*****";
$url = "https://eksisozluk.com/giris";
$cookie= "cookies.txt";
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookie);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookie);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$response = curl_exec($ch);
if (curl_errno($ch)) die(curl_error($ch));
$dom = new DomDocument();
$dom->loadHTML($response);
$tokens = $dom->getElementsByTagName("meta");
for ($i = 0; $i < $tokens->length; $i++)
{
$meta = $tokens->item($i);
if($meta->getAttribute('name') == 'csrf-token')
$token = $meta->getAttribute('content');
}
$postinfo = "UserName=".$username."&Password=".$password."&_csrf=".$token;
echo $token; //debug info
curl_setopt($ch, CURLOPT_RETURNTRANSFER, false);
curl_setopt($curl, CURLOPT_AUTOREFERER, 1);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookie);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookie);
curl_setopt($ch, CURLOPT_POSTFIELDS, $postinfo);
$html = curl_exec($ch);
print($html);
if (curl_errno($ch)) print curl_error($ch);
curl_close($ch);
我正在打印一个 cookie。只是给你一个空白sheet。我收到错误消息。
您尝试在获取 cookie 之前发送登录凭据,但该网站要求您在登录之前已经有一个 cookie。此外,该网站使用了一个 CSRF token,您需要在登录之前获取它登录,但你没有。另外,您的用户名和密码需要进行urlencode,但您没有对其进行urlencode,例如@是错误的,它应该是Username=pik123%40gmail.com
(@
urlencoded是%40
),用户名变量也称为 UserName
,而不是 Username
、
首先使用正常的 GET 请求获取登录页面,这将为您提供所需的 cookie 和 CSRF 令牌,
然后解析出CSRF token,用application/x-www-form-urlencoded
格式的cookie和CSRF token向登录页面发送POST请求,CSRF为__RequestVerificationToken
token 和 UserName
作为用户名(注意这里的 CaPiTaLiZaTiOn,它是 UserName
,而不是 Username
),Password
作为密码,以及一个看似硬编码的参数称为 ReturnUrl
,它只包含 /
(urlencoded ofc,即 %2F
,例如 ReturnUrl=%2F
),您应该登录(您的 cookie 会话现在将登录) ,前提是您有有效的凭据。
带有 hhb_curl library 的示例(负责 cookie 处理和 curl 错误检查,将 curl 错误转换为 RuntimeExceptions):
<?php
declare (strict_types = 1);
require_once('hhb_.inc.php');
$username = "pik123@gmail.com";
$password = "Bf*****";
$hc = new hhb_curl('', true);
// get cookie and csrc token:
$html = $hc->exec('https://eksisozluk.com/giris')->getStdOut();
$domd = @DOMDocument::loadHTML($html);
$xp = new DOMXPath($domd);
// grab the login form (it contains the csrf token, among other things)
$login_form = $xp->query("//form[contains(@action,'/giris')]")->item(0);
$login_parameters = array();
foreach ($login_form->getElementsByTagName("input") as $input) {
$login_parameters[$input->getAttribute("name")] = $input->getAttribute("value");
}
// the CSRF token is called `__RequestVerificationToken`, and $login_parameters now contains roughly:
// array(
// '__RequestVerificationToken' => 'qTk2Ik0glfV8W1WckmrVkVXujQE8C1eTqMEe36SP-PPUXDn88GG0XYxif3ZMIVGZH08-MEbbtD7i7Q4ymxuasveDZL-WaHQH22r33fOdsqQ1',
// 'ReturnUrl' => '/',
// 'UserName' => '',
// 'Password' => '',
// 'RememberMe' => 'false',
// );
assert(isset($login_parameters['UserName']));
assert(isset($login_parameters['Password']));
$login_parameters['UserName'] = $username;
$login_parameters['Password'] = $password;
// log in
$html = $hc->setopt_array(array(
CURLOPT_POST => 1,
CURLOPT_POSTFIELDS => http_build_query($login_parameters)
))->exec()->getStdOut();
// check for login errors:
$domd = @DOMDocument::loadHTML($html);
$xp = new DOMXPath($domd);
$login_errors = array();
foreach ($xp->query("//*[contains(@class,'validation-error')]") as $login_error) {
$login_error = trim($login_error->textContent);
if (!empty($login_error)) {
$login_errors[] = $login_error;
}
}
unset($login_error);
if (!empty($login_errors)) {
throw new \RuntimeException("eksisozluk login errors: " . print_r($login_errors, true));
}
输出:
$ php wtf4.php
PHP Fatal error: Uncaught RuntimeException: eksisozluk login errors: Array
(
[0] => captcha'yı yanlış girdiniz.
)
in /cygdrive/c/projects/misc/wtf4.php:46
Stack trace:
#0 {main}
thrown in /cygdrive/c/projects/misc/wtf4.php on line 46
- 因为
pik123@gmail.com
/ Bf*****
不是有效的登录凭据。
我想使用 PHP CURL 库登录 https 上的页面。重新加载此页面。但我做不到。我无法从服务器或本地主机建立连接。
$username = "pik123@gmail.com";
$password = "Bf*****";
$url = "https://eksisozluk.com/giris";
$cookie= "cookies.txt";
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookie);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookie);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$response = curl_exec($ch);
if (curl_errno($ch)) die(curl_error($ch));
$dom = new DomDocument();
$dom->loadHTML($response);
$tokens = $dom->getElementsByTagName("meta");
for ($i = 0; $i < $tokens->length; $i++)
{
$meta = $tokens->item($i);
if($meta->getAttribute('name') == 'csrf-token')
$token = $meta->getAttribute('content');
}
$postinfo = "UserName=".$username."&Password=".$password."&_csrf=".$token;
echo $token; //debug info
curl_setopt($ch, CURLOPT_RETURNTRANSFER, false);
curl_setopt($curl, CURLOPT_AUTOREFERER, 1);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookie);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookie);
curl_setopt($ch, CURLOPT_POSTFIELDS, $postinfo);
$html = curl_exec($ch);
print($html);
if (curl_errno($ch)) print curl_error($ch);
curl_close($ch);
我正在打印一个 cookie。只是给你一个空白sheet。我收到错误消息。
您尝试在获取 cookie 之前发送登录凭据,但该网站要求您在登录之前已经有一个 cookie。此外,该网站使用了一个 CSRF token,您需要在登录之前获取它登录,但你没有。另外,您的用户名和密码需要进行urlencode,但您没有对其进行urlencode,例如@是错误的,它应该是Username=pik123%40gmail.com
(@
urlencoded是%40
),用户名变量也称为 UserName
,而不是 Username
、
首先使用正常的 GET 请求获取登录页面,这将为您提供所需的 cookie 和 CSRF 令牌,
然后解析出CSRF token,用application/x-www-form-urlencoded
格式的cookie和CSRF token向登录页面发送POST请求,CSRF为__RequestVerificationToken
token 和 UserName
作为用户名(注意这里的 CaPiTaLiZaTiOn,它是 UserName
,而不是 Username
),Password
作为密码,以及一个看似硬编码的参数称为 ReturnUrl
,它只包含 /
(urlencoded ofc,即 %2F
,例如 ReturnUrl=%2F
),您应该登录(您的 cookie 会话现在将登录) ,前提是您有有效的凭据。
带有 hhb_curl library 的示例(负责 cookie 处理和 curl 错误检查,将 curl 错误转换为 RuntimeExceptions):
<?php
declare (strict_types = 1);
require_once('hhb_.inc.php');
$username = "pik123@gmail.com";
$password = "Bf*****";
$hc = new hhb_curl('', true);
// get cookie and csrc token:
$html = $hc->exec('https://eksisozluk.com/giris')->getStdOut();
$domd = @DOMDocument::loadHTML($html);
$xp = new DOMXPath($domd);
// grab the login form (it contains the csrf token, among other things)
$login_form = $xp->query("//form[contains(@action,'/giris')]")->item(0);
$login_parameters = array();
foreach ($login_form->getElementsByTagName("input") as $input) {
$login_parameters[$input->getAttribute("name")] = $input->getAttribute("value");
}
// the CSRF token is called `__RequestVerificationToken`, and $login_parameters now contains roughly:
// array(
// '__RequestVerificationToken' => 'qTk2Ik0glfV8W1WckmrVkVXujQE8C1eTqMEe36SP-PPUXDn88GG0XYxif3ZMIVGZH08-MEbbtD7i7Q4ymxuasveDZL-WaHQH22r33fOdsqQ1',
// 'ReturnUrl' => '/',
// 'UserName' => '',
// 'Password' => '',
// 'RememberMe' => 'false',
// );
assert(isset($login_parameters['UserName']));
assert(isset($login_parameters['Password']));
$login_parameters['UserName'] = $username;
$login_parameters['Password'] = $password;
// log in
$html = $hc->setopt_array(array(
CURLOPT_POST => 1,
CURLOPT_POSTFIELDS => http_build_query($login_parameters)
))->exec()->getStdOut();
// check for login errors:
$domd = @DOMDocument::loadHTML($html);
$xp = new DOMXPath($domd);
$login_errors = array();
foreach ($xp->query("//*[contains(@class,'validation-error')]") as $login_error) {
$login_error = trim($login_error->textContent);
if (!empty($login_error)) {
$login_errors[] = $login_error;
}
}
unset($login_error);
if (!empty($login_errors)) {
throw new \RuntimeException("eksisozluk login errors: " . print_r($login_errors, true));
}
输出:
$ php wtf4.php
PHP Fatal error: Uncaught RuntimeException: eksisozluk login errors: Array
(
[0] => captcha'yı yanlış girdiniz.
)
in /cygdrive/c/projects/misc/wtf4.php:46
Stack trace:
#0 {main}
thrown in /cygdrive/c/projects/misc/wtf4.php on line 46
- 因为
pik123@gmail.com
/Bf*****
不是有效的登录凭据。