Как получить и опубликовать информацию в одном запросе cURL? - PullRequest
0 голосов
/ 12 июня 2019

Можно ли получить value из input, а также post информацию в том же cURL запросе?

Причина: Я пытаюсь войти здесь , используя cURL, однако форма входа генерирует уникальный ключ в value из input с именем form_key. Итак, я хочу сначала получить это значение, а затем опубликовать имя пользователя и пароль для успешного входа в систему.

PHP (не работает, выдает пустую страницу без исходного кода):

$ch2 = curl_init();
curl_setopt($ch2, CURLOPT_URL, "https://b2b.chiemsee.com/customer/account/login/");
curl_setopt($ch2, CURLOPT_FOLLOWLOCATION, true); // to allow redirections
//curl_setopt($ch2, CURLOPT_SSL_VERIFYPEER, FALSE); // to avoid error
curl_setopt($ch2, CURLOPT_POST, true); // to send info
curl_setopt($ch2, CURLOPT_POSTFIELDS, $data);
curl_setopt($ch2, CURLOPT_COOKIEJAR, 'cookie.txt'); // to save cookie data for login
curl_setopt($ch2, CURLOPT_RETURNTRANSFER, true); // to get the html
$response2 = curl_exec($ch2);
curl_close($ch2);

$html = new simple_html_dom();
$html->load($response2);

$val = $html->find('input[name=form_key]');
$form_key = $val[0]->value;

$data = array(
    'form_key' => $form_key,
    'login[username]' => 'myusername',
    'login[password]' => 'mypassword',
    'send' => '',
);

P.S. Когда я вхожу вручную и проверяю консоль браузера -> сеть -> сообщение -> заголовки / параметры, я получаю следующее: -

form_key: viiRqZigH0YPC9wu
login[username]: myusername
login[password]: mypassword
send: 

UPDATE. ДВА ОТДЕЛЬНЫХ ЗАПРОСА СЛУЧАЯ (все еще работают):

* * Включают в тысячу двадцать-один ( 'simple_html_dom.php'); * * 1 022
$ch2 = curl_init();
curl_setopt($ch2, CURLOPT_URL, "https://b2b.chiemsee.com/customer/account/login/");
curl_setopt($ch2, CURLOPT_FOLLOWLOCATION, true); // to allow redirections
curl_setopt($ch2, CURLOPT_COOKIEJAR, 'cookie.txt'); // to save cookie data for login
curl_setopt($ch2, CURLOPT_RETURNTRANSFER, true); // to get the html
$response2 = curl_exec($ch2);
curl_close($ch2);

$html = new simple_html_dom();
$html->load($response2);

$val = $html->find('input[name=form_key]');
$form_key = $val[0]->value;

$data = array(
    'form_key' => $form_key,
    'login[username]' => 'myusername',
    'login[password]' => 'mypassword',
    'send' => 'Anmelden'
);

$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, "https://b2b.chiemsee.com/customer/account/login/");
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true); // to allow redirections
//curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, FALSE); // to avoid error
curl_setopt($ch, CURLOPT_POST, true); // to send info
curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
curl_setopt($ch, CURLOPT_COOKIEFILE, 'cookie.txt'); // to read data
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); // to get the html
$response = curl_exec($ch);
if (curl_error($ch)) {
    $error_msg = curl_error($ch);
    var_dump($error_msg);
    exit;
}
curl_close($ch);
echo $response;

Ответы [ 2 ]

2 голосов
/ 12 июня 2019

Итак, немного о том, что происходит.

form_key, по-видимому, используется как форма защиты от CSRF, в частности, это токен синхронизатора .

Короче говоря, пользователь посещает веб-страницу, веб-страница создает сеанс для пользователя и генерирует уникальный токен.Затем сервер присоединяет этот уникальный токен к форме как скрытое поле.Когда пользователь отправляет эту форму, она отправляется с этим скрытым полем, и сервер может перекрестно ссылаться на то, что полученный токен совпадает с отправленным.

Однако важной частью является то, что сервер должен знать, кто пользователь, и это делается в течение сеанса.Сеанс поддерживается с помощью файла cookie сеанса, поэтому файл cookie сеанса необходим.

Чтобы правильно смоделировать реального пользователя, вам необходимо сохранить куки-файлы, которые сервер отправляет вам при первом посещении, это делается с помощью CURLOPT_COOKIEJAR:

$ch2 = curl_init();
curl_setopt($ch2, CURLOPT_URL, "https://b2b.chiemsee.com/customer/account/login/");
curl_setopt($ch2, CURLOPT_FOLLOWLOCATION, true); // to allow redirections
//curl_setopt($ch2, CURLOPT_SSL_VERIFYPEER, FALSE); // to avoid error
curl_setopt($ch2, CURLOPT_POST, true); // to send info
curl_setopt($ch2, CURLOPT_POSTFIELDS, $data);
curl_setopt($ch2, CURLOPT_COOKIEJAR, 'cookie.txt'); // to save session cookie
curl_setopt($ch2, CURLOPT_RETURNTRANSFER, true); // to get the html
$response2 = curl_exec($ch2);
curl_close($ch2);

после того, как вы это сделалии получил токен CSRF, очистив страницу, которую необходимо отправить, вместе с соответствующими файлами cookie:

$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, "https://b2b.chiemsee.com/customer/account/loginPost/"); //Make sure you have the correct URL
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true); // to allow redirections
//curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, FALSE); // to avoid error
curl_setopt($ch, CURLOPT_POST, true); // to send info
curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
curl_setopt($ch, CURLOPT_COOKIEFILE, 'cookie.txt'); // to read cookie data
curl_setopt($ch2, CURLOPT_COOKIEJAR, 'cookie.txt'); // optional, this will update existing cookies and add new ones if needed.
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); // to get the html
$response = curl_exec($ch);
if (curl_error($ch)) {
    $error_msg = curl_error($ch);
    var_dump($error_msg);
    exit;
}
curl_close($ch);
echo $response;

Это должно позволить серверу загрузить правильный сеанс, для которого токен CSRF был создан в первую очередь.и затем проверьте тот токен, который вы отправляете.

Как примечание: Причина токена проста.Если я создаю веб-страницу, которая обманывает пользователей, чтобы они могли публиковать их непосредственно на другой веб-странице, то этот токен является частью данных, к которым у меня никогда не будет доступа, так как я делюсь ими напрямую только с пользователем, поэтому третьи стороны не могут получить к нему доступ.Это может усложнить реализацию таких автоматизаций, как ваша, но это очень эффективно для безопасности пользователей.

1 голос
/ 12 июня 2019

То, что вы спрашиваете, невозможно.Не из-за ограничений cURL или PHP, а просто из-за причинности.Рассмотрим логический набор выполняемых шагов.Для того, чтобы отправить запрос на вход в систему, вы должны сначала знать form_key.Чтобы узнать form_key, вы должны сначала запросить страницу входа.

Проще говоря, вы не можете использовать информацию, которой у вас еще нет.

  • Сделайте первый HTTP-запрос для получения информации о форме.(В частности, значение form_key, которое вам нужно.)
  • Сделайте второй HTTP-запрос для отправки информации для входа в систему, включая данные, которые вы извлекли из первого запроса.

Там нетпричина попытаться сделать это за один шаг.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...