我正在使用 curl_multi 发出异步请求:http://php.net/manual/en/function.curl-multi-init.php
脚本向所有给定的 URL 发送请求,这对于我正在做的事情来说有点快。有没有办法降低请求率?
最佳答案
function asyncCurl($url){
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_FRESH_CONNECT, true);
curl_setopt($ch, CURLOPT_TIMEOUT, 1);
curl_exec($ch);
curl_close($ch);
}
$timeout = 3; // in seconds
$urls = array(...);
foreach($urls as $url){
asyncCurl($url);
sleep($timeout);
}
如果您需要获得响应,仍然可以通过在您的服务器上创建“后台进程”类型的东西来完成。这将需要 2 个脚本而不是一个。
background.php
function curl($url){
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
$a = curl_exec($ch);
curl_close($ch);
return $a;
}
$response = curl($_GET['url']);
// code here to handle the response
doRequest.php(或其他任何内容,这是您将在浏览器中调用的文件)
function asyncCurl($url){
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, "mydomain.com/background.php?url=".urlencode($url));
curl_setopt($ch, CURLOPT_FRESH_CONNECT, true);
curl_setopt($ch, CURLOPT_TIMEOUT, 1);
curl_exec($ch);
curl_close($ch);
}
$timeout = 3; // in seconds
$urls = array(...);
foreach($urls as $url){
asyncCurl($url);
sleep($timeout);
}
这里的想法是 PHP 是单线程的,但没有理由不能让多个 PHP 进程同时运行。唯一的缺点是您必须在一个脚本上发出请求并在另一个脚本上处理响应。
选项 3:输出可用时立即显示。
这个方法和上面的完全一样,只不过是用javascript创建了一个新的php进程。您没有标记 javascript,但这是完成两者的唯一方法
- 带超时的异步请求
和
响应可用时立即显示响应
doRequest.php
<?php $urls = array(); // fill with your urls $timeout = 3; // in seconds if (isset($_GET['url'])) { $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, $_GET['url']); $a = curl_exec($ch); curl_close($ch); echo $a; exit; } ?><html> <body> <div id='results'></div> <script> var urls = <?php echo json_encode($urls); ?>; var currentIndex = 0; function doRequest(url) { var xhttp = new XMLHttpRequest(); xhttp.onreadystatechange = function () { if (xhttp.readyState == 4 && xhttp.status == 200) { document.getElementById("results").insertAdjacentHTML("beforeend", "<hr>" + xhttp.responseText); } }; xhttp.open("GET", "doRequest.php?url=" + encodeURIComponent(url), true); xhttp.send(); } var index=0; function startLoop(){ var url = urls[index]; doRequest(url); setTimeout(function(){ index++; if('undefined' != urls[index]) startLoop(); }, <?php echo $timeout*1000; ?>); } startLoop(); </script> </body>
发生的事情是你的服务器正在为每个 url 创建一个新的请求,然后使用普通的 curl 来获取响应,但是我们没有使用 curl 来创建新进程,而是使用 ajax,它本质上是异步的并且能够创建多个 PHP 进程并等待响应。
祝一切顺利!
关于php - 使 curl_multi 'sleep' 或等待发送下一个请求,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34642620/