php - 在 foreach 循环上执行 cURL 请求,交替返回 http 代码 200 和 0
问题描述
我有一个使用 curl_multi_excec 函数的代码,但它返回 http 代码 200 和 0,这意味着交替。这是我的代码片段:
try{
$allproducts = json_decode(self::getProductbyEan());
//An array that will contain all of the information
//relating to each request.
$requests = array();
//Initiate a multiple cURL handle
$mh = curl_multi_init();
//Loop through each URL.
foreach($allproducts as $k => $url){
$url = 'https://nartastaging.retailpath.com.au/cgi-bin/WebObjects/NARTAStaging.woa/ra/Product/'.$url->id.'.json';
$requests[$k] = array();
$requests[$k]['url'] = $url;
//Create a normal cURL handle for this particular request.
$requests[$k]['curl_handle'] = curl_init($url);
//Configure the options for this request.
curl_setopt($requests[$k]['curl_handle'], CURLOPT_RETURNTRANSFER, true);
curl_setopt($requests[$k]['curl_handle'], CURLOPT_FOLLOWLOCATION, true);
curl_setopt($requests[$k]['curl_handle'], CURLOPT_TIMEOUT, 10);
curl_setopt($requests[$k]['curl_handle'], CURLOPT_CONNECTTIMEOUT, 10);
curl_setopt($requests[$k]['curl_handle'], CURLOPT_SSL_VERIFYHOST, false);
curl_setopt($requests[$k]['curl_handle'], CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($requests[$k]['curl_handle'], CURLOPT_HTTPAUTH, CURLAUTH_BASIC);
curl_setopt($requests[$k]['curl_handle'], CURLOPT_USERPWD, "$login:$password");
//Add our normal / single cURL handle to the cURL multi handle.
curl_multi_add_handle($mh, $requests[$k]['curl_handle']);
}
//Execute our requests using curl_multi_exec.
$stillRunning = false;
curl_multi_setopt ( $mh , CURLMOPT_MAXCONNECTS, 5);
do {
curl_multi_exec($mh, $stillRunning);
} while ($stillRunning);
//Loop through the requests that we executed.
foreach($requests as $k => $request){
//Remove the handle from the multi handle.
curl_multi_remove_handle($mh, $request['curl_handle']);
//Get the response content and the HTTP status code.
$requests[$k]['http_code'] = curl_getinfo($request['curl_handle'], CURLINFO_HTTP_CODE);
//Close the handle.
curl_close($requests[$k]['curl_handle']);
}
//Close the multi handle.
curl_multi_close($mh);
//var_dump the $requests array for example purposes.
print_r($requests);
}catch(Exception $e){
wp_die($e->getMessage());
}
这是结果的输出:
[0] => Array
(
[url] => https://nartastaging.retailpath.com.au/cgi-bin/WebObjects/NARTAStaging.woa/ra/Product/1155551.json
[curl_handle] => Resource id #75
[http_code] => 200
)
[1] => Array
(
[url] => https://nartastaging.retailpath.com.au/cgi-bin/WebObjects/NARTAStaging.woa/ra/Product/6345345334.json
[curl_handle] => Resource id #76
[http_code] => 0
)
[2] => Array
(
[url] => https://nartastaging.retailpath.com.au/cgi-bin/WebObjects/NARTAStaging.woa/ra/Product/45456456.json
[curl_handle] => Resource id #77
[http_code] => 200
)
[3] => Array
(
[url] => https://nartastaging.retailpath.com.au/cgi-bin/WebObjects/NARTAStaging.woa/ra/Product/145555.json
[curl_handle] => Resource id #78
[http_code] => 0
)
[4] => Array
(
[url] => https://nartastaging.retailpath.com.au/cgi-bin/WebObjects/NARTAStaging.woa/ra/Product/2qw22w.json
[curl_handle] => Resource id #79
[http_code] => 200
)
[5] => Array
(
[url] => https://nartastaging.retailpath.com.au/cgi-bin/WebObjects/NARTAStaging.woa/ra/Product/5025155024034.json
[curl_handle] => Resource id #80
[http_code] => 0
)
[6] => Array
(
[url] => https://nartastaging.retailpath.com.au/cgi-bin/WebObjects/NARTAStaging.woa/ra/Product/5025155023983.json
[curl_handle] => Resource id #81
[http_code] => 200
)
如您所见,http_code 结果显示在某些情况下它返回 200 和 0。任何帮助将不胜感激。提前致谢
解决方案
我重构了您的代码以使其更易于理解。此外,我使用免费的外部 API 来检查代码。到目前为止,我没有看到任何问题。也许问题就在你$url
身边(' https://nartastaging.retailpath.com.au/cgi-bin/WebObjects/NARTA ...')。我的意思是,也许该 API 有一些检查以在并行运行时禁用某些请求......
<?php declare(strict_types=1);
final class MultiRequestForProduct
{
/** @var string */
private $baseUrl;
public function __construct(string $baseUrl)
{
$this->baseUrl = $baseUrl;
}
public function execute(array $products): array
{
$multiCurl = $this->initMultiCurl();
$requests = $this->initRequests($products);
$this->execMultiCurl($multiCurl, $requests);
$requests = $this->addHttpCodeToRequest($multiCurl, $requests);
curl_multi_close($multiCurl);
return $requests;
}
private function initMultiCurl()
{
$multiCurl = curl_multi_init();
curl_multi_setopt($multiCurl, CURLMOPT_MAXCONNECTS, 2);
return $multiCurl;
}
private function initRequests(array $products): array
{
foreach ($products as $k => $url) {
$url = sprintf($this->baseUrl, $url->id);
$requests[$k] = [
'url' => $url,
'curl_handle' => curl_init($url),
];
$handler = curl_init($url);
curl_setopt($handler, CURLOPT_RETURNTRANSFER, true);
curl_setopt($handler, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($handler, CURLOPT_TIMEOUT, 10);
curl_setopt($handler, CURLOPT_CONNECTTIMEOUT, 10);
curl_setopt($handler, CURLOPT_SSL_VERIFYHOST, false);
curl_setopt($handler, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($handler, CURLOPT_HTTPAUTH, CURLAUTH_BASIC);
// curl_setopt($handler, CURLOPT_USERPWD, "$login:$password");
$requests[$k]['curl_handle'] = $handler;
}
return $requests;
}
private function execMultiCurl($multiCurl, array $requests): void
{
foreach ($requests as $request) {
curl_multi_add_handle($multiCurl, $request['curl_handle']);
}
$stillRunning = false;
do {
curl_multi_exec($multiCurl, $stillRunning);
} while ($stillRunning);
}
private function addHttpCodeToRequest($multiCurl, array $requests): array
{
foreach ($requests as $k => $request) {
curl_multi_remove_handle($multiCurl, $request['curl_handle']);
$requests[$k]['http_code'] = curl_getinfo($request['curl_handle'], CURLINFO_HTTP_CODE);
curl_close($requests[$k]['curl_handle']);
}
return $requests;
}
}
// Usage:
$products = [];
foreach (range(1, 8) as $i) {
$product = new \stdClass;
$product->id = $i;
$products[] = $product;
}
$multiRequest = new MultiRequestForProduct($baseUrl = 'https://httpbin.org/get?id=%d');
$requests = $multiRequest->execute($products);
var_dump($requests);
推荐阅读
- javascript - TaxCalculator 函数 Javascript 代码不起作用
- javascript - node.js - 从异步函数推送到数组
- scala - 一个专门的参数类/特征可以扩展另一个特征吗?
- android - 我已将我的 Google API 密钥限制为我的移动应用程序包。还能被盗吗?
- java - Spring-boot:应用程序无法启动
- java - 控制面板和终端之间的 Java 版本不匹配
- javascript - 在类成员函数中使用常量变量的最快方法?
- html - 日期字段的占位符 Asp.net HtmlHelper
- javascript - 如何使用 html 和 javascript 中的输入更改连接多个 id 以更改颜色
- user-interface - ListTile 中的图像