PHP 中的异步 curl 请求 [英] Async curl request in PHP
问题描述
我正在 PHP 中执行两个 curl 发布请求.它们的外观如下:
I'm executing two curl post requests in PHP. Here's how they look like:
//Onfleet API credentials
$username = 'xxxxx';
$api_onfleet = 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$url_onfleet = "https://onfleet.com/api/v2/tasks";
curl_setopt($curl, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1_2);
$request = $url.'api/mail.send.json';
// Generate curl request
$session = curl_init($request);
// Tell curl to use HTTP POST
curl_setopt ($session, CURLOPT_POST, true);
// Tell curl that this is the body of the POST
curl_setopt ($session, CURLOPT_POSTFIELDS, $params);
// Tell curl not to return headers, but do return the response
curl_setopt($session, CURLOPT_HEADER, false);
curl_setopt($session, CURLOPT_RETURNTRANSFER, true);
// obtain response
$response = curl_exec($session);
curl_close($session);
// Post the Pickup task to Onfleet
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url_onfleet);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($ch, CURLOPT_USERPWD, $api_onfleet);
curl_setopt($ch, CURLOPT_HTTPAUTH, CURLAUTH_BASIC);
curl_setopt($ch, CURLOPT_ENCODING, "");
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, '{"destination":{"address":{"unparsed":"'.$pickup_address.'"},"notes":"'.$comments.'"},"recipients":[{"name":"'.$name.'","phone":"+61'.$phone.'","notes":"Number of riders: '.$riders.'"}],"completeBefore":'.$timestamp.',"pickupTask":"yes","autoAssign":{"mode":"distance"}}');
$result_pickup = curl_exec($ch);
curl_close($ch);
// Post the Dropoff task to Onfleet
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $url_onfleet);
curl_setopt($curl, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_USERPWD, $api_onfleet);
curl_setopt($curl, CURLOPT_HTTPAUTH, CURLAUTH_BASIC);
curl_setopt($curl, CURLOPT_ENCODING, "");
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, '{"destination":{"address":{"unparsed":"'.$dropoff_address.'"},"notes":"'.$comments.'"},"recipients":[{"name":"'.$name.'","phone":"+61'.$phone.'","notes":"Number of riders: '.$riders.'"}],"autoAssign":{"mode":"distance"}}');
$result_dropoff = curl_exec($curl);
curl_close($curl);
他们正在工作,但有时,第二个 curl post 请求没有执行.
They are working, but sometimes, the second curl post request is not executed.
我想同时执行这两个请求.
I'd like to execute this two requests at the same time.
我该怎么做?请注意,它们在后域中采用不同的选项.
How can I do that? Please note that they take different options in the postfields.
感谢您的帮助!
推荐答案
所以你想做的是异步执行 cUrl 请求.
So what you want to do is asynchronous execution of the cUrl Requests.
因此您需要一个用于 php 的异步/并行处理库.
So you would need a asynchronous/parallel processing library for php.
用于 php 的突出线程库之一是 pthreads
One of the prominent threading libraries for php is pthreads
您需要先获取 dll/so 文件并将其保存在 php/ext
目录中,然后在 php.ini
中启用该扩展.
You would need to first get the dll/so file and save it in the php/ext
dir, and enable that extension in php.ini
.
之后,此代码将完成您的工作:
After That, this code would do your job:
class Request1 extends Thread {
$username = 'xxxxx';
$api_onfleet = 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$url_onfleet = "https://onfleet.com/api/v2/tasks";
public function run() {
curl_setopt($curl, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1_2);
$request = $this->url.'api/mail.send.json';
// Generate curl request
$session = curl_init($request);
// Tell curl to use HTTP POST
curl_setopt ($session, CURLOPT_POST, true);
// Tell curl that this is the body of the POST
curl_setopt ($session, CURLOPT_POSTFIELDS, $params);
// Tell curl not to return headers, but do return the response
curl_setopt($session, CURLOPT_HEADER, false);
curl_setopt($session, CURLOPT_RETURNTRANSFER, true);
// obtain response
$response = curl_exec($session);
curl_close($session);
}
}
class Request2 extends Thread {
$username = 'xxxxx';
$api_onfleet = 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$url_onfleet = "https://onfleet.com/api/v2/tasks";
public function run() {
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url_onfleet);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($ch, CURLOPT_USERPWD, $this->api_onfleet);
curl_setopt($ch, CURLOPT_HTTPAUTH, CURLAUTH_BASIC);
curl_setopt($ch, CURLOPT_ENCODING, "");
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, '{"destination":{"address":{"unparsed":"'.$pickup_address.'"},"notes":"'.$comments.'"},"recipients":[{"name":"'.$name.'","phone":"+61'.$phone.'","notes":"Number of riders: '.$riders.'"}],"completeBefore":'.$timestamp.',"pickupTask":"yes","autoAssign":{"mode":"distance"}}');
$result_pickup = curl_exec($ch);
curl_close($ch);
// Post the Dropoff task to Onfleet
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, $this->url_onfleet);
curl_setopt($curl, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($curl, CURLOPT_USERPWD, $this->api_onfleet);
curl_setopt($curl, CURLOPT_HTTPAUTH, CURLAUTH_BASIC);
curl_setopt($curl, CURLOPT_ENCODING, "");
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, '{"destination":{"address":{"unparsed":"'.$dropoff_address.'"},"notes":"'.$comments.'"},"recipients":[{"name":"'.$name.'","phone":"+61'.$phone.'","notes":"Number of riders: '.$riders.'"}],"autoAssign":{"mode":"distance"}}');
$result_dropoff = curl_exec($curl);
curl_close($curl);
}
}
$req1 = new Request1();
$req1->start();
$req2 = new Request2();
$req2->start();
因此,基本上您需要创建一个扩展 Thread
类的类,并且您想要异步(而不是并行)运行的所有内容都将放入函数 run()类的代码>.
So, basically you need to create a class which extends the Thread
class and everything you want to run asynchronously (rather parallely), would be put in the function run()
of the class.
当你想启动线程时,只需在变量中实例化类,然后调用对象的启动方法,如$threadsObject->start()
和中的所有内容run()
将在另一个线程上执行.
When you want to start the thread just instantiate the class in a variable, and call the start method of the object, like $threadsObject->start()
and everything in the run()
would be executed on another thread.
参考:
就是这样.
另一种方法是使用内置的异步cURL函数一>.
The other way is to use the built in asynchronous cURL functions.
因此,当使用 curl_multi_*
时,您的代码将类似于:
So, when using curl_multi_*
, your code would look something like:
$username = 'xxxxx';
$api_onfleet = 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
$url_onfleet = "https://onfleet.com/api/v2/tasks";
curl_setopt($curl, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1_2);
$request = $url.'api/mail.send.json';
// Generate curl request
$session = curl_init($request);
// Tell curl to use HTTP POST
curl_setopt ($session, CURLOPT_POST, true);
// Tell curl that this is the body of the POST
curl_setopt ($session, CURLOPT_POSTFIELDS, $params);
// Tell curl not to return headers, but do return the response
curl_setopt($session, CURLOPT_HEADER, false);
curl_setopt($session, CURLOPT_RETURNTRANSFER, true);
// Post the Pickup task to Onfleet
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url_onfleet);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
curl_setopt($ch, CURLOPT_USERPWD, $api_onfleet);
curl_setopt($ch, CURLOPT_HTTPAUTH, CURLAUTH_BASIC);
curl_setopt($ch, CURLOPT_ENCODING, "");
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, '{"destination":{"address":{"unparsed":"'.$pickup_address.'"},"notes":"'.$comments.'"},"recipients":[{"name":"'.$name.'","phone":"+61'.$phone.'","notes":"Number of riders: '.$riders.'"}],"completeBefore":'.$timestamp.',"pickupTask":"yes","autoAssign":{"mode":"distance"}}');
$mh = curl_multi_init();
curl_multi_add_handle($mh,$session);
curl_multi_add_handle($mh,$ch);
$active = null;
//execute the handles
do {
$mrc = curl_multi_exec($mh, $active);
} while ($mrc == CURLM_CALL_MULTI_PERFORM);
while ($active && $mrc == CURLM_OK) {
if (curl_multi_select($mh) != -1) {
do {
$mrc = curl_multi_exec($mh, $active);
} while ($mrc == CURLM_CALL_MULTI_PERFORM);
}
}
//close the handles
curl_multi_remove_handle($mh, $ch1);
curl_multi_remove_handle($mh, $ch2);
curl_multi_close($mh);
推荐阅读:
这篇关于PHP 中的异步 curl 请求的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!