当前位置: 首页 > 知识库问答 >
问题:

PHP:对外部Oath2 API的Curl POST请求

慕容晔
2023-03-14

我试着描述一下我们的情况:

  • 我们有一个Wordpress网站,需要连接到Oath2 API
  • 我对API和PHP的使用经验很少
  • 我们正在使用一个PHP-Oath2库,可以在这里找到:https://github.com/adoy/PHP-OAuth2/tree/master/src/OAuth2

我们卡住的库中的方法是 executeRequest。这种方法可以在 https://github.com/adoy/PHP-OAuth2/blob/master/src/OAuth2/Client.php 的第404行(哦,讽刺)上找到

现在,就像我说的,我在PHP方面几乎没有经验,所以我的调试方式只是在脚本中给定点回显变量的状态。尽管这可能是业余的,但我至少可以验证url和参数是否正确。我可以打印完整的URL(虚拟参数值ofc):

请注意以下使用的参数:代码redirect_urigrant_typen client_idclient_Secret

https://oauth.smartschool.be/OAuth/index/token?code=irsyB0VSmg4V5dVjHFgdl85iRvvu3gYpsuIE4cOk

执行此请求时,将收到 JSON 错误消息。这是正常的,因为我不能给你我们的client_id和client_secret:

{"error":"error_occured","error_description":"Client authentication failed."}

当我在浏览器中手动执行时(使用正确的参数值),我得到了想要的JSON结果:

{ " access _ token ":" fa 4 a 6 S4 axsaxsfacc 56 C4 ACA 8 acac 4c 4 q 6 D5 z 4 fsv "," token_type":"Bearer "," expires_in":3600," refresh _ token ":" x 5s 1 AQ 56 AQ 6 bhz 56 agy 6 SCB 9845465 czxqde 56a " }

问题是,当CURL构建并执行这个POST请求时,我得到一个错误的JSON结果:

{"error":"error_occured","error_description":"The request is missing a required parameter, includes an invalid parameter value, includes a parameter more than once, or is otherwise malformed. Check the \u0022code\u0022 parameter."}

我可以验证以下CURL选项的状态(请注意,代码绕过了ssl验证,在Client.php文件的第462行):

  • CURLOPT_RETURNTRANSFER=true
  • CURLOPT_SSL_VERIFYPEER=false
  • CURLOPT_SSL_VERIFYHOST=false
  • CURLOPT_CUSTOMREQUEST='POST'
  • CURLOPT_POST=true
  • CURLOPT_POSTFIELDS=url编码参数字符串

示例:code = irsyb 0 vsmg 4v 5 dvjhfgdl 85 irvvu 3 gypsuie 4 cook

    < Li > CURLOPT _ URL = https://oauth.smartschool.be/OAuth/index/token < li>CURLOPT_HTTPHEADER =

当像这样执行这个 Curl 处理程序时:

$result = curl_exec($ch);

他确实成功地联系了 API 并返回了结果,但 JSON 结果显示参数错误,声称代码不正确。但我知道这是正确的,因为当我通过浏览器手动执行请求时,它可以工作。如果您直接转到没有参数的 https://oauth.smartschool.be/OAuth/index/token,则会出现完全相同的错误。

这让我想知道curl是否传递了任何参数。

你能告诉我你是否在提供的ifno的某个地方发现了错误,也许在curl选项中?或者你能引导我找到一种正确的方法来调试这个curl执行(请记住,如果我在Wordpress上,如果这很重要的话)。

请让我知道,如果这个职位缺乏所需的信息。提前感谢。

--编辑:

库代码由以下代码行(同样是虚拟客户端 ID 和机密)触发。此方法可在 https://github.com/adoy/PHP-OAuth2/blob/master/src/OAuth2/Client.php 的第 211 行找到

$client = new Client('5d6t5ev5a6d8', 'pada9c54a6sc');
$callBackUrl = 'https://mycallbackurl.com/my-page';
$myResponse = $client->getAccessToken('https://oauth.smartschool.be/OAuth/index/token', 'authorization_code', ['code'=> $_GET['code'], 'redirect_uri' => $callBackUrl]);

为了确保万无一失,我已经删除了将header选项放入空数组的代码。但是用CURLINFO_HEADER_OUT调试时,结果还是一样的。它确实默认为Content-Type:application/x-www-form-urlencoded。下面是完整的curl_getinfo()数组:

数组 ( [url] =

然而,结果保持不变(仍然表示根本没有传递任何参数):

数组 ( [结果] =

有没有办法从这个curl请求中打印参数/post字段/body,以验证所有信息都已发送?

-编辑2:

使用Tobias提供的httbin.org/post链接后,我得到了以下结果:

Array ( 
    [args] => Array 
        (
        ) 

    [data] => 
    [files] => Array 
        ( 
        ) 

    [form] => Array 
        ( 
            [client_id] => 5d6t5ev5a6d8
            [client_secret] => pada9c54a6sc
            [code] => fa4a6s4axsaxxsfacc56c4aca8acac4q6d5z4fsv
            [grant_type] => authorization_code 
            [redirect_uri] => https://mycallbackurl.com/my-page
        ) 

    [headers] => Array 
        ( 
            [Accept] => */* 
            [Connection] => close 
            [Content-Length] => 216 
            [Content-Type] => application/x-www-form-urlencoded 
            [Host] => httpbin.org 
        ) 

    [json] => 
    [origin] => 83.xxx.xx.xx
    [url] => https://httpbin.org/post 
) 

将此与Tobias的示例进行比较,我没有看到任何值得注意的差异。我假设这意味着我们的POST请求至少包含所有必需的数据。我们仍然一无所知,那么API不接受参数的可能原因是什么。如果您想出其他可能的解决方案,请不要犹豫将其附加。感谢这个转储链接,这真的很有用!

共有1个答案

葛智敏
2023-03-14

在浏览器中进行测试与实际代码之间存在差异:在浏览器中,将变量作为 GET 参数传递,而在代码中发送 POST 正文。

为了调试这些问题,我经常发现在转到PHP之前使用CLI<code>curl<code>更容易。当我像这样发送请求时(注意<code>内容类型

curl -X POST --data "code=irsyB0VSmg4V5dVjHFgdl85iRvvu3gYpsuIE4cOk&redirect_uri=https%3A%2F%2Fmycallbackurl.com%2Fmy-page%2F&grant_type=authorization_code&client_id=5d6t5ev5a6d8&client_secret=pada9c54a6sc" "https://oauth.smartschool.be/OAuth/index/token" -H "Content-Type: application/x-www-form-urlencoded"
{"error":"error_occured","error_description":"Client authentication failed."}

当我强行发送没有这个头的请求时,我能够重现您的错误。这实际上并不容易,因为使用< code> - data会自动添加它:

curl -X POST --data "code=irsyB0VSmg4V5dVjHFgdl85iRvvu3gYpsuIE4cOk&redirect_uri=https%3A%2F%2Fmycallbackurl.com%2Fmy-page%2F&grant_type=authorization_code&client_id=5d6t5ev5a6d8&client_secret=pada9c54a6sc" "https://oauth.smartschool.be/OAuth/index/token" -H "Content-Type: "
{"error":"error_occured","error_description":"The request is missing a required parameter, includes an invalid parameter value, includes a parameter more than once, or is otherwise malformed. Check the \u0022grant_type\u0022 parameter."}

您需要确保您的代码发送请求时带有标头:Content-Type: application/x-www-form-urlencoded

我猜PHP-curl在使用POST(字段)(类似于CLI版本)时也会隐式添加它,您的问题可能是您“强制”将CURLOPT_HTTPHEADER设置为空数组,从而将其删除。

要调试正在发送的标头,可以使用:

curl_setopt($ch, CURLINFO_HEADER_OUT, true);
// curl_exec
$information = curl_getinfo($ch);
print_r($information);

编辑:

实际上,更好的调试方法是更改帖子所指向的OAuth URLhttps://httpbin.org/post.这将只是镜像发送给它的所有内容,因此,然后转储您得到的响应,它应该如下所示:

Array
(
    [result] => Array
        (
            [args] => Array
                (
                )

            [data] =>
            [files] => Array
                (
                )

            [form] => Array
                (
                    [client_id] => 5d6t5ev5a6d8
                    [client_secret] => pada9c54a6sc
                    [code] => irsyB0VSmg4V5dVjHFgdl85iRvvu3gYpsuIE4cOk
                    [grant_type] => authorization_code
                    [redirect_uri] => https://mycallbackurl.com/my-page
                )

            [headers] => Array
                (
                    [Accept] => */*
                    [Connection] => close
                    [Content-Length] => 180
                    [Content-Type] => application/x-www-form-urlencoded
                    [Host] => httpbin.org
                )

            [json] =>
            [origin] => 217.***.***.***
            [url] => https://httpbin.org/post
        )

    [code] => 200
    [content_type] => application/json
)

您可以很有希望地确定从那里发送(或不发送)的内容,包括主体数据。不幸的是,甚至<code>curl<code>的详细模式都没有显示这一点。

 类似资料:
  • 在Xcode8/Swift3.0中注册推送通知? 是否有方法在appdelegate和func应用程序(_application:UIApplication,didFinishLaunchingWithOptions LaunchOptions:[NSObject:AnyObject]?)之外请求requestAuthorization(选项:[.Badge,.Alert,.Sound])->布尔

  • 在使用morgan中间件记录日志时,我注意到服务器日志中出现了一些频繁且令人担忧的请求。 相关记录器代码 因此,日志的示例如下 不幸的是,我不知道如何重现这样的错误。这是一个潜在的漏洞吗?原木锻造?我在哪里可以找到进一步的信息? 具体来说,这一行的url是“GET”http://example.com/path.php HTTP/1.1”,其中example.com不是我的域,我的服务器也没有设置

  • 我想向外部API发出HTTP Post请求,但当我试图从React with axios执行此操作时,我遇到了CORS错误(请求的资源上不存在“Access Control Allow Origin”头)。同时,在.NET中发出此请求时,一切似乎都正常。我不知道为什么会这样,也许有人能弄明白。 响应请求: ...NET请求:

  • 我已经使用wiremck配置了几个存根。我需要检查通过Rest API向外部服务器发送请求的客户端。但是当我配置存根时,出于某种原因,存根的请求被截断,主机(模拟外部服务器)被截断。 application.properties Rest客户端 < li>wiremock配置 测试 我有多个不同地址主机的配置。每台主机都有自己的端口。当我通过endpointRest控制器发送请求时,主机地址不会被

  • 问题内容: 我有一个运行Elasticsearch的e2 ubuntu实例,尽管它在本地运行良好,但无法使用Windows PC进行连接(错误是“无法连接到远程服务器”)。 我已经在相同的ubuntu实例上设置了Apache,并在同一台Windows计算机上工作,并且我可以毫无问题地ping该实例。我的Amazon安全组允许tcp从所有IP地址访问所有端口。 我认为这是一个ES配置问题,尽管我添加

  • 问题内容: 我使用以下PHP函数: 每当我在特定服务器上执行此操作时,结果都是空的。当我在其他地方执行此操作时,结果将是页面内容可能是什么。但是,当我在结果为空的服务器上时,请在本地使用该功能- 无需访问外部URL(),它就 可以 工作。 现在,我很确定它与特定的php.ini配置有关。但是我不确定的是 哪 一个。请帮忙。 问题答案: 您正在寻找的设置是。 您有两种不更改php.ini的方法来解决