PHP cURL只需要发送,不需要等待响应

PHP cURL只需要发送,不需要等待响应,php,curl,Php,Curl,我需要一个PHP cURL配置,以便我的脚本能够发送请求并忽略API发送的答案 curl_setopt($ch,CURLOPT_URL,$url); curl_setopt($ch,CURLOPT_POST,count($fields)); curl_setopt($ch,CURLOPT_POSTFIELDS,$fields_string); // curl_setopt($ch, CURLOPT_RETURNTRANSFER, false); //curl_setopt($ch, CURLOP

我需要一个PHP cURL配置,以便我的脚本能够发送请求并忽略API发送的答案

curl_setopt($ch,CURLOPT_URL,$url);
curl_setopt($ch,CURLOPT_POST,count($fields));
curl_setopt($ch,CURLOPT_POSTFIELDS,$fields_string);
// curl_setopt($ch, CURLOPT_RETURNTRANSFER, false);
//curl_setopt($ch, CURLOPT_TIMEOUT_MS, 100);
$result = curl_exec($ch);
echo $result;
curl_close ($ch);
我试着加上: //curl_setopt($ch,CURLOPT_RETURNTRANSFER,false); //curl_setopt($ch,CURLOPT_TIMEOUT_MS,100)

但是它不能正常工作,并且API Web服务器没有接收到请求

原因是我正在向API发送大量请求,因此我的脚本非常慢,因为它等待每个请求


非常感谢您的帮助。

您如何判断请求是否成功?您需要等待至少来自服务器的状态代码来确定。如果存在延迟问题,请查看curlmulti API以并行执行多个请求。您应该能够设置写入回调函数,以便在返回状态代码后中止接收返回的数据。

如果可能,您可以在后台运行(使用)

发送者文件示例。/ajax/Sender.php

下面我们尝试在不等待答案的情况下对php脚本进行ping

    $url = 'https://127.0.0.1/ajax/received.php';
    $curl = curl_init();                
    $post['test'] = 'examples daata'; // our data todo in received
    curl_setopt($curl, CURLOPT_URL, $url);
    curl_setopt ($curl, CURLOPT_POST, TRUE);
    curl_setopt ($curl, CURLOPT_POSTFIELDS, $post); 

    curl_setopt($curl, CURLOPT_USERAGENT, 'api');

    curl_setopt($curl, CURLOPT_TIMEOUT, 1); 
    curl_setopt($curl, CURLOPT_HEADER, 0);
    curl_setopt($curl,  CURLOPT_RETURNTRANSFER, false);
    curl_setopt($curl, CURLOPT_FORBID_REUSE, true);
    curl_setopt($curl, CURLOPT_CONNECTTIMEOUT, 1);
    curl_setopt($curl, CURLOPT_DNS_CACHE_TIMEOUT, 10); 

    curl_setopt($curl, CURLOPT_FRESH_CONNECT, true);

    curl_exec($curl);   

    curl_close($curl);  
接收到的文件示例。/ajax/Received.php

编辑2019如果您使用fastcgi,只需完成fastcgi和浏览器的紧密连接,但脚本将一直工作到最后

fastcgi_finish_request(); $this->db->query('UPDATE new_hook_memory SET new=new+1 WHERE id=1');
旧版本:

ob_end_clean(); //if our framework have turn on ob_start() we don't need bufering respond up to this script will be finish 
    header("Connection: close\r\n"); //send information to curl is close
    header("Content-Encoding: none\r\n"); //extra information 
    header("Content-Length: 1"); //extra information
    ignore_user_abort(true); //script will be exisits up to finish below query even web browser will be close before sender get respond

    //we doing here what we would like do
    $this->db->query('UPDATE new_hook_memory SET new=new+1 WHERE id=1');    

现在有点晚了,但对任何感兴趣的人来说,解决这个问题的方法是将
CURLOPT_RETURNTRANSFER
设置为
TRUE
,而不是
false
。通过这种方式,
curl\u exec
函数立即返回一个值,而不是在返回前等待请求完成-即,它以异步方式而不是同步方式运行

例如:

curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
这对我很有效。
在PHP7.1.14Windows上进行测试

这两个解决方案对我来说很好 (当然已经很久了,但我不认为这个问题过时了)

使用文件获取内容

  //url of php to be called

$url = "example.php/test?id=1";

  //this will set the minimum time to wait before proceed to the next line to 1 second

$ctx = stream_context_create(['http'=> ['timeout' => 1]]);

file_get_contents($url,null,$ctx);

  //the php will read this after 1 second 
  //url of php to be called

$url = "example.php/test?id=1";

$test = curl_init();

  //this will set the minimum time to wait before proceed to the next line to 100 milliseconds

curl_setopt_array($test,[CURLOPT_URL=>$url,CURLOPT_TIMEOUT_MS=>100,CURLOPT_RETURNTRANSFER=>TRUE]);

curl_exec($test);

  //this line will be executed after 100 milliseconds

curl_close ($test); 
使用卷曲

  //url of php to be called

$url = "example.php/test?id=1";

  //this will set the minimum time to wait before proceed to the next line to 1 second

$ctx = stream_context_create(['http'=> ['timeout' => 1]]);

file_get_contents($url,null,$ctx);

  //the php will read this after 1 second 
  //url of php to be called

$url = "example.php/test?id=1";

$test = curl_init();

  //this will set the minimum time to wait before proceed to the next line to 100 milliseconds

curl_setopt_array($test,[CURLOPT_URL=>$url,CURLOPT_TIMEOUT_MS=>100,CURLOPT_RETURNTRANSFER=>TRUE]);

curl_exec($test);

  //this line will be executed after 100 milliseconds

curl_close ($test); 
在这两种情况下,被调用的php必须设置
ignore\u user\u abort(true)


在这两种情况下都不会打印结果,但要注意设置的超时时间,它需要大于被调用的php开始生成结果所需的时间。

您不在代码中添加任何内容吗?这是没有用的。这是可行的,但如果您设置的超时太小(在我的情况下为10毫秒),它会在请求完全发送之前被中断。一些解释:此代码生成一个cURL错误代码28:«操作在1000毫秒后超时,接收到的字节数为-1中的0»。(
$data
为false)。此代码段使用的技巧在于忽略此错误,因为它不会传播到PHP。cURL发送的查询将继续使用。但是您不知道该查询是否已被主机接受。@skrol29此示例适用于包含ip或主机的单向流,您需要信任您的主机或ip。简单的解决方案就是不要等待响应。如果您想使用重要的数据并确保安全,那么应该使用不同的方法(如rabitmq)来进行更多的控制。即使你不需要知道卷曲的结果。就像ping到php一样,要进行count+1这样的操作,现在就不能用php7发送异步请求或使用线程吗?Reza询问了其他问题设置CURLOPT_RETURNTRANSFER为true,确保我立即获得返回值,而不必等待请求完成。这不是OP所要求的吗?如果您正在呼叫的服务器延迟30秒给您提供值和响应,您如何能够立即获得值?Curl_setopt总是立即返回,因为在启动连接之前需要设置选项。这个答案没有任何意义,是错误的,并且没有回答OP的问题它是curl_exec(不是curl_setopt),它将立即返回或等待外部服务器响应,具体取决于使用curl_setopt的CURLOPT_RETURNTRANSFER set的值。谢谢你指出这一点-我已经编辑了我的答案。这并没有解决问题。它相当于后台curl,仍然有一个进程等待响应,消耗计算资源。这不是最好的主意。如果打印响应,如何禁用它?@Hassaan:
curl\u setopt($ch,CURLOPT\u RETURNTRANSFER,TRUE)
@MarcoDemaio这将使脚本尽可能地等待响应know@l00k,我想Hassaan在他的评论中询问了如何不打印调用
curl_exec($ch)的结果这似乎比人们想象的要难。这里有一篇关于这个问题的好文章和三种可能的解决方案。TLDR:您可以使用
pfsockopen
打开持久套接字连接或fork curl进程,或者如果您不关心实际请求的延迟(例如,在日志场景中),您可以将请求记录到日志文件中,并让后台进程(如cron)使用日志条目在带外发送请求。