php 登录curl 代码未按预期工作

2024-04-30

我正在尝试使用 php 中的curl 函数登录到特定页面。请检查下面的代码。我在 banggood.com 连接我的电子邮件和密码,然后我想重定向到另一个私人页面,但它无法按预期工作。我没有收到任何错误。我被重定向到此页面(https://www.banggood.com/index.php?com=account https://www.banggood.com/index.php?com=account)使用下面的代码。登录后,我想访问我的订单所在的私人页面。任何帮助表示赞赏。

//The username or email address of the account.
define('EMAIL', '[email protected] /cdn-cgi/l/email-protection');

//The password of the account.
define('PASSWORD', 'mypassword');

//Set a user agent. This basically tells the server that we are using Chrome ;)
define('USER_AGENT', 'Mozilla/5.0 (Windows NT 5.1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/35.0.2309.372 Safari/537.36');

//Where our cookie information will be stored (needed for authentication).
define('COOKIE_FILE', 'cookie.txt');

//URL of the login form.
define('LOGIN_FORM_URL', 'https://www.banggood.com/login.html');

//Login action URL. Sometimes, this is the same URL as the login form.
define('LOGIN_ACTION_URL', 'https://www.banggood.com/login.html');


//An associative array that represents the required form fields.
//You will need to change the keys / index names to match the name of the form
//fields.
$postValues = array(
    'email' => EMAIL,
    'password' => PASSWORD
);

//Initiate cURL.
$curl = curl_init();

//Set the URL that we want to send our POST request to. In this
//case, it's the action URL of the login form.
curl_setopt($curl, CURLOPT_URL, LOGIN_ACTION_URL);

//Tell cURL that we want to carry out a POST request.
curl_setopt($curl, CURLOPT_POST, true);

//Set our post fields / date (from the array above).
curl_setopt($curl, CURLOPT_POSTFIELDS, http_build_query($postValues));

//We don't want any HTTPS errors.
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);

//Where our cookie details are saved. This is typically required
//for authentication, as the session ID is usually saved in the cookie file.
curl_setopt($curl, CURLOPT_COOKIEJAR, COOKIE_FILE);

//Sets the user agent. Some websites will attempt to block bot user agents.
//Hence the reason I gave it a Chrome user agent.
curl_setopt($curl, CURLOPT_USERAGENT, USER_AGENT);

//Tells cURL to return the output once the request has been executed.
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);

//Allows us to set the referer header. In this particular case, we are
//fooling the server into thinking that we were referred by the login form.
curl_setopt($curl, CURLOPT_REFERER, LOGIN_FORM_URL);

//Do we want to follow any redirects?
curl_setopt($curl, CURLOPT_FOLLOWLOCATION, false);

//Execute the login request.
curl_exec($curl);

//Check for errors!
if(curl_errno($curl)){
    throw new Exception(curl_error($curl));
}

//We should be logged in by now. Let's attempt to access a password protected page
curl_setopt($curl, CURLOPT_URL, 'https://www.banggood.com/index.php?com=account&t=ordersList');

//Use the same cookie file.
curl_setopt($curl, CURLOPT_COOKIEJAR, COOKIE_FILE);

//Use the same user agent, just in case it is used by the server for session validation.
curl_setopt($curl, CURLOPT_USERAGENT, USER_AGENT);

//We don't want any HTTPS / SSL errors.
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, false);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);

//Execute the GET request and print out the result.
curl_exec($curl);

你做错了几件事:

  1. 您尝试在拥有 Cookie 会话之前登录,但该网站要求您在发送登录请求之前拥有 Cookie 会话。

  2. 有一个 CSRF 令牌与您的 cookie 会话绑定,此处称为at,您需要从登录页面 html 中解析出来并提供您的登录请求,您的代码不会获取该请求。

  3. 最重要的是,有一个验证码图像与您的 cookie 会话相关联,您需要获取并解析该图像,以及您需要将谁的文本附加到您的登录请求中,而您的代码完全忽略了这些文本。

  4. 您的登录请求需要标头x-requested-with: XMLHttpRequest- 但你的代码没有添加该标头。

  5. 您的登录请求需要这些字段com=account and t=submitLoginPOST 数据中的字段,但您的代码没有添加其中任何一个(您尝试将它们添加到您的 URL,但它们不应该出现在 url 中,它们应该出现在 POST 数据中,又名您的 $postValues 数组,而不是网址)

您需要执行以下操作:

  • 首先对登录页面执行普通的 GET 请求。这将为您提供会话 cookie id、CSRF 令牌以及验证码图像的 url。
  • 存储 cookie id 并确保为所有进一步的请求提供它,然后解析出 csrf 令牌(它在 html 中,看起来像<input type="hidden" name="at" value="5aabxxx5dcac0" />),以及验证码图像的 url(每个 cookie 会话都不同,因此不要对其进行硬编码)。
  • 然后获取验证码图像,解决它,并将它们全部添加到您的登录请求的 POST 数据中,以及用户名、密码、验证码答案,com and t,并添加http标头x-requested-with: XMLHttpRequest也发送到登录请求https://www.banggood.com/login.html,那么您应该已登录!

这是一个使用示例实现hhb_curl https://github.com/divinity76/hhb_.inc.php/blob/master/hhb_.inc.php#L407用于Web请求(它是一个curl_包装器,负责处理cookie,将无声的curl_错误转换为RuntimeExceptions等),用于解析CSRF令牌的DOMDocument,以及用于破解验证码的deathbycaptcha.com的api。

Ps: the example code won't work until you provide a real credited deathbycaptcha.com api username/password on line 6 and 7, also the captcha looks so simple that I think breaking it could be automated if you're sufficiently motivated, I'm not. - edit, seems they improved their captcha since i wrote that, it looks very difficult now. Also, the banggood account is just a temporary testing account, no harm comes of it being compromised, which obviously happens when I post the username/password here)

<?php

declare(strict_types = 1);
require_once ('hhb_.inc.php');
$banggood_username = '[email protected] /cdn-cgi/l/email-protection';
$banggood_password = '[email protected] /cdn-cgi/l/email-protection';
$deathbycaptcha_username = '?';
$deathbycaptcha_password = '?';

$hc = new hhb_curl ( '', true );
$html = $hc->exec ( 'https://www.banggood.com/login.html' )->getStdOut ();
$domd = @DOMDocument::loadHTML ( $html );
$xp = new DOMXPath ( $domd );
$csrf_token = $xp->query ( '//input[@name="at"]' )->item ( 0 )->getAttribute ( "value" );
$captcha_image_url = 'https://www.banggood.com/' . $domd->getElementById ( "get_login_image" )->getAttribute ( "src" );
$captcha_image = $hc->exec ( $captcha_image_url )->getStdOut ();

$captcha_answer = deathbycaptcha ( $captcha_image, $deathbycaptcha_username, $deathbycaptcha_password );

$html = $hc->setopt_array ( array (
        CURLOPT_POST => 1,
        CURLOPT_POSTFIELDS => http_build_query ( array (
                'com' => 'account',
                't' => 'submitlogin',
                'email' => $banggood_username,
                'pwd' => $banggood_password,
                'at' => $csrf_token,
                'login_image_code' => $captcha_answer 
        ) ),
        CURLOPT_HTTPHEADER => array (
                'x-requested-with: XMLHttpRequest' 
        ) 
) )->exec ()->getStdOut ();
var_dump ( // $hc->getStdErr (),
$html );

function deathbycaptcha(string $imageBinary, string $apiUsername, string $apiPassword): string {
    $hc = new hhb_curl ( '', true );
    $response = $hc->setopt_array ( array (
            CURLOPT_URL => 'http://api.dbcapi.me/api/captcha',
            CURLOPT_POST => 1,
            CURLOPT_HTTPHEADER => array (
                    'Accept: application/json' 
            ),
            CURLOPT_POSTFIELDS => array (
                    'username' => $apiUsername,
                    'password' => $apiPassword,
                    'captchafile' => 'base64:' . base64_encode ( $imageBinary )  // use base64 because CURLFile requires a file, and i cba with tmpfile() .. but it would save bandwidth.
            ),
            CURLOPT_FOLLOWLOCATION => 0 
    ) )->exec ()->getStdOut ();
    $response_code = $hc->getinfo ( CURLINFO_HTTP_CODE );
    if ($response_code !== 303) {
        // some error
        $err = "DeathByCaptcha api retuned \"$response_code\", expected 303, ";
        switch ($response_code) {
            case 403 :
                $err .= " the api username/password was rejected";
                break;
            case 400 :
                $err .= " we sent an invalid request to the api (maybe the API specs has been updated?)";
                break;
            case 500 :
                $err .= " the api had an internal server error";
                break;
            case 503 :
                $err .= " api is temorarily unreachable, try again later";
                break;
            default :
                {
                    $err .= " unknown error";
                    break;
                }
        }
        $err .= ' - ' . $response;
        throw new \RuntimeException ( $err );
    }
    $response = json_decode ( $response, true );
    if (! empty ( $response ['text'] ) && $response ['text'] !== '?') {
        return $response ['text']; // sometimes the answer might be available right away.
    }
    $id = $response ['captcha'];
    $url = 'http://api.dbcapi.me/api/captcha/' . urlencode ( $id );
    while ( true ) {
        sleep ( 10 ); // check every 10 seconds
        $response = $hc->setopt ( CURLOPT_HTTPHEADER, array (
                'Accept: application/json' 
        ) )->exec ( $url )->getStdOut ();
        $response = json_decode ( $response, true );
        if (! empty ( $response ['text'] ) && $response ['text'] !== '?') {
            return $response ['text'];
        }
    }
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

php 登录curl 代码未按预期工作 的相关文章

  • 计算特定产品类别的购物车商品数量

    我试图仅从 WooCommerce 中的特定产品类别获取购物车中的商品数量 我正在为一家酒厂做一个网站 它有酒精和非酒精产品 所有葡萄酒都属于 葡萄酒 主类别或类别 ID 34 其下有许多子类别和产品 对于属于此类别的任何商品 我需要知道此
  • 通过php将mp3转换为ogg

    我有一个网站 用户可以上传音乐并将其转换为 mp3 但我需要 mp3 和 ogg 文件支持才能以 html5 播放音乐 那么 有没有可以将mp3转换为ogg的php脚本呢 使用 ffmpeg 您可以直接从 php 脚本执行命令
  • preg_match 所有以@开头的单词?

    我对正则表达式不太确定 所以我不得不问你 如何用 PHP 判断字符串中是否包含以 开头的单词 例如我有一个像 This is for codeworxx 这样的字符串 我很抱歉 但我没有任何起点 希望你能帮忙 谢谢 萨沙 好的 谢谢你的结果
  • PHP 和 DOM 文档

    我有一个关于 DOMDocument 的使用和创建 XML 的问题 我有一个 PHP 程序 加载到 XML 文件中 处理XML的每个节点 行 将其发送到另一个进程 然后该进程返回一个 XML 元素 我获取节点的字符串表示形式 以便可以创建
  • MySQL 最佳实践:SELECT 子递归尽可能提高性能?

    我想选择一个根项目及其子项 使其性能尽可能高 我更喜欢使用嵌套集模型 但这次表结构遵循邻接模型 有关嵌套集和邻接模型的更多信息 http mikehillyer com articles managing hierarchical data
  • 如何处理 PHP 中浮点数的奇怪舍入

    众所周知 浮点运算并不总是完全准确 但是如何处理它的不一致之处呢 As an example in PHP 5 2 9 this doesn t happen in 5 3 echo round 14 99225 4 14 9923 ech
  • 未找到“MongoId”类(带有 MongoDB Doctrine 的 Zend 框架)

    我目前正在尝试将 MongoDB 与 ZendFramework 中的 Doctrine 集成 我做了很多教程 在 StackOverflow 或其他地方 但没有任何效果 我一步步按照教程进行操作 http www bigwisu com
  • 匹配括号内任何字符的正则表达式

    尝试创建一个与括号内的任何字符匹配的正则表达式 我的正则表达式模式是这样的 preg match listanswer answer 括号内的所有字符串都是匹配模式 但问题是 当我尝试匹配例如 this word sample data 它
  • 如何使用 PHP 查找目录中的前 5 个文件?

    如何使用 PHP 列出按字母顺序排序的目录中的前 5 个文件或目录 Using scandir array slice array filter scandir path to dir is file 0 5 The array filte
  • HTTP_REFERER 返回 NULL,$_SERVER 中不存在密钥

    使用以来第一次 SERVER HTTP REFERER 它给了我NULL因此 当我做var dump SERVER the HTTP REFERER密钥不存在 我还尝试使用不同的浏览器和不同的网站访问网站 但没有结果 该网站在基于 Linu
  • PHP,文本从数据库中回显,没有换行,全部一体

    我的数据库中有一个长文本 从 php mayadmin 来看它看起来很好 但是当我将它回显到页面时 它会丢失所有格式 即没有新行 全部都在一个块中 有任何想法吗 Thanks 可能是因为换行符是 n 并且 html 想要 br 所以使用nl
  • 在 Laravel 中按数据透视表 create_at 排序

    在我的数据库中 我有以下表格 courses id 名称 创建时间 更新时间 students id 名称 创建时间 更新时间 课程 学生 id course id student id created at updated at 我正在尝
  • 对更改运行 PHPUnit 测试

    每当磁盘上的文件发生更改时 我想运行 PHPUnit 测试 或至少其中的一个子集 与您可以使用 进行的操作非常相似 咕噜手表 https github com gruntjs grunt contrib watch blob master
  • 如何在PHP中将图像从内存上传到AWS S3?

    所以我目前有一个使用 AWS S3 上传图像的上传系统 这是代码 Upload image to S3 s3 Aws S3 S3Client factory array key gt mykey secret gt myskey try s
  • 使用 Spring 的 REST 多部分混合请求(文件+json)

    我需要将一个文件和一个 json 一起发送到我的 Spring 控制器 我有以下控制器类 Controller RequestMapping perform public class PerformController RequestMap
  • 如何使用多个数据库设置 symfony 3 学说迁移?

    我在验证和更新模式时努力让 symfony doctrine 排除数据库视图 我第一次尝试没有教条迁移 看到这个问题 https stackoverflow com questions 46775200 symfony 3 doctrine
  • 仅在 Chrome 上我收到此错误:Uncaught TypeError: Illegal constructor [关闭]

    Closed 这个问题是无法重现或由拼写错误引起 help closed questions 目前不接受答案 当我在 Chrome 上加载 jQuery 时 我会收到此错误 Uncaught TypeError Illegal constr
  • 使用 PHP 创建图表并导出为 PDF

    我正在寻找有关使用 PHP 创建图表的建议 我还希望能够将这些图表导出到 PDF 文档 我目前正在使用谷歌图表 但我不喜欢将我的所有信息发送到谷歌的想法 我更喜欢自己的托管解决方案 我见过很多 Flash 解决方案 但我不知道有什么方法可以
  • 准备好的语句需要 0 个参数,给定 1 个参数..,使用 php 手册示例 [重复]

    这个问题在这里已经有答案了 我直接从 php 手册示例中获取了这个 它几乎与我需要的相同 但我仍然收到此错误 有人可以告诉我我错过了什么吗 stmt link gt prepare SELECT obitBody Photo FROM tn
  • 如何检查号码是否是巴基斯坦用户的手机号码而不是固定电话号码

    我所做的是从开头删除 92 或 0092 并使用以下代码检查它是否是巴基斯坦人的有效手机号码 if preg match 3 0 4 0 9 number 1 Pakistani mobile number else not a pakis

随机推荐

  • 用正则表达式重写YAML frontmatter

    我想使用 Jekyll 将我的 WordPress 网站转换为 GitHub 上的静态网站 我使用了一个插件 将我的 62 篇帖子以 Markdown 形式导出到 GitHub 我现在在每个文件的开头都有这些带有额外 frontmatter
  • 如果通过 SQL 查询结果没有找到记录,则应为 0

    我正在使用火鸟 我需要以下结果 但我没有得到我需要的结果 我尝试了以下查询 SELECT CASE EXTRACT MONTH FROM pd Date WHEN 1 THEN January WHEN 2 THEN February WH
  • MVC 中的外键注释

    我有两张桌子 State StateID int StateName string City CityID int StateID int CityName string 我正在使用代码优先方法开发 MVC4 代码 我正在使用State a
  • 剑道网格服务器端过滤并且不工作

    我正在使用 Kendo 网格 具有服务器端过滤 排序和分页功能 这是我初始化网格的代码 在此代码中 服务器端分页和虚拟滚动正常工作 但过滤和短路不起作用 在任何请求中 我都会得到这个 请求参数的类型 HttpPost public Json
  • 数组奇偶排序

    我有一个数组 其中有一些数字 现在我想对单独的数组中的偶数进行排序 对单独的奇数进行排序 有没有 API 可以做到这一点 我试过这样 int array sort 5 12 3 21 8 7 19 102 201 int even sort
  • 如何删除 XML::Simple 输出中的 标记?

    我正在使用 Perl 创建一个 XML 文件 XML 简单 http search cpan org dist XML Simple模块 我成功创建了 XML 文件 但问题是我遇到了
  • Cabal 在 NixOS 上构建时找不到外部库

    我正在尝试使用 cabal2nix 在 NixOS 上构建一个内部 Haskell 项目 它包装 并因此依赖 一个外部库 在 Ubuntu 上可以通过以下方式构建 wget设置源 然后运行make make install ldconfig
  • Python 记录器应该作为参数传递吗? [关闭]

    Closed 这个问题是基于意见的 help closed questions 目前不接受答案 我们正在开发的 Python 应用程序需要一个记录器 一位同事认为应该在每个使用它的类中创建和配置记录器 我的观点是 它应该在应用程序启动时创建
  • Excel VBA - 将 .xls 附加到文件名以打开文件

    我有代码可以打开带有可变日期的文件 如下所示 如果不在输入框中输入 m d y xls 此代码将无法运行 我只想在输入框中输入 m d y 请看一下并让我知道我缺少什么 谢谢 Dim wbkOpen As Workbook Dim strF
  • 如何使用 spring-test-junit5 进行嵌套测试?

    我一直在玩JUnit 5 http junit org junit5 and 弹簧测试junit5 https github com sbrannen spring test junit5 然后我尝试使用嵌套测试 http junit or
  • Firebase 云功能 - Stripe Connect Webhook 未触发

    我正在尝试设置我的 stripe webhook 以便在创建 更新 Stripe Connect 帐户或执行任何操作时自动调用 Firebase 云函数 仅当我手动转到 Stripe 仪表板 gt Webhooks 并点击 发送测试 Web
  • 在给定时间后停止 java 中的线程 - 不起作用

    我有一个复杂的函数 优化 可能会进入循环或只是花费太多时间 并且允许的时间由用户设置 因此 我试图在单独的线程中运行该函数 并在超过最大时间时停止它 我使用类似于下面的代码 但它不起作用 所以 int timeMax 2 time in m
  • 如何处理WPF中Grid Splitter生成的事件?

    我想要一个事件处理程序来处理移动网格拆分器时的事件 我不确定是否有一个 如果没有 我想我可以在行大小更改时生成一个事件 Thanks 您可以更改行的大小 但 GridSplitter 本身是一个 Thumb 因此有自己的事件 例如 Drag
  • 数据库索引:是好事、坏事还是浪费时间?

    这里通常建议添加索引作为性能问题的补救措施 我只讨论读取和查询 我们都知道索引会使写入速度变慢 多年来 我在 DB2 和 MSSQL 上多次尝试过这种补救措施 但结果总是令人失望 我的发现是 无论索引会让事情变得更好是多么 明显 事实证明查
  • glutPostRedisplay 不在循环内工作

    我试图让一个人在 y 轴上跳跃 所以我使用 2 秒的循环 第一秒它应该向下移动并弯曲膝盖 第二秒它应该向上移动 然后在起始位置完成 现在我刚刚开始让这个人在第一秒内跪下并弯曲膝盖 我还没有编写动画的其余部分 问题是 glutPostRedi
  • 带有反应导航的自定义图标 5

    我正在尝试将自定义图标与反应选项卡导航一起使用 但是 所有教程和文档 总是只涵盖通过 Ionicons 或 Materialdesign 实现图标 有没有办法实现我自己的图标 代码如下
  • 使用 const shared_ptr<> 的基于范围的 for 循环

    我有一个容器shared ptr lt gt 例如Avector
  • 如何将 DateTime 转换为自 1970 年以来的秒数?

    我正在尝试将 C DateTime 变量转换为 Unix 时间 即自 1970 年 1 月 1 日以来的秒数 看起来 DateTime 实际上是作为自 0001 年 1 月 1 日以来的 刻度 数来实现的 我目前的想法是从我的 DateTi
  • 使用虚假数据生成回形针图像上传 - Ruby on Rails Populator / Faker Gems

    我目前正在尝试用一堆假数据填充项目的开发数据库 以模拟数百篇文章 用户的外观和操作方式 我研究了不同的宝石来完成任务 例如 Factory Girl 但文档非常缺乏 我没有得到它 但最终使用了 Populator 和 Faker gems
  • php 登录curl 代码未按预期工作

    我正在尝试使用 php 中的curl 函数登录到特定页面 请检查下面的代码 我在 banggood com 连接我的电子邮件和密码 然后我想重定向到另一个私人页面 但它无法按预期工作 我没有收到任何错误 我被重定向到此页面 https ww