PHP 5.6.0beta1 released

curl_multi_select

(PHP 5)

curl_multi_selectAttend une activité sur n'importe quelle connexion curl_multi

Description

int curl_multi_select ( resource $mh [, float $timeout = 1.0 ] )

Patiente tant qu'il y a de l'activité sur une des connexions curl_multi.

Liste de paramètres

mh

Un gestionnaire cURL multiple retourné par la fonction curl_multi_init().

timeout

Durée maximale, en secondes, à attendre une réponse.

Valeurs de retour

Retourne le nombre de sockets contenues dans le jeu de sockets, en cas de succès. En cas d'échec, la fonction retournera -1 sur un échec de sélection ou lors d'un dépassement du délai d'attente (depuis l'appel du sous système de sélection).

Voir aussi

add a note add a note

User Contributed Notes 5 notes

up
4
Alex Palmer
1 year ago
On php 5.3.18+ be aware that curl_multi_select() may return -1 forever until you call curl_multi_exec().
See https://bugs.php.net/bug.php?id=63411 for more information.
up
4
vigo dot von dot harrach at gmx dot de
1 year ago
curl_multi_select($mh, $timeout) simply blocks for $timeout seconds while curl_multi_exec() returns CURLM_CALL_MULTI_PERFORM. Otherwise, it works as intended, and blocks until at least one connection has completed or $timeout seconds, whatever happens first.

For that reason, curl_multi_exec() should always be wrapped:

<?php
 
function full_curl_multi_exec($mh, &$still_running) {
    do {
     
$rv = curl_multi_exec($mh, $still_running);
    } while (
$rv == CURLM_CALL_MULTI_PERFORM);
    return
$rv;
  }
?>

With that, the core of "multi" processing becomes (ignoring error handling for brevity):

<?php
  full_curl_multi_exec
($mh, $still_running); // start requests
 
do { // "wait for completion"-loop
   
curl_multi_select($mh); // non-busy (!) wait for state change
   
full_curl_multi_exec($mh, $still_running); // get new state
   
while ($info = curl_multi_info_read($mh)) {
     
// process completed request (e.g. curl_multi_getcontent($info['handle']))
   
}
  } while (
$still_running);
?>

Note that after starting requests, retrieval is done in the background - one of the better shots at parallel processing in PHP.
up
3
public at grik dot net
5 years ago
This function blocks the calling process until there is activity on any of the connections opened by the curl_multi interface, or until the timeout period has expired.
In other words, it waits for data to be received in the opened connections.

Internally it fetches socket pointers with "curl_multi_fdset()" and runs the "select()" C function.
It returns in 3 cases:
1. Activity is detected on any socket;
2. Timeout has ended (second parameter);
3. Process received any signal (#man kill).

The function returns an integer:
* In case of activity it returns a number, usually 1.
I suppose, it returns the number of connections with activity detected.
* If timeout expires it returns 0
* In case of error it returns -1

Thanks for attention, hope this helps.
up
2
Anonymous
6 months ago
In 5.3.9+, curl_multi_select always returns -1. If this is your case, just wait a bit and then proceed like nothing ever happened:
<?php
do { 
   
$mrc = curl_multi_exec($multi, $active); 
} while (
$mrc == CURLM_CALL_MULTI_PERFORM); 
   
while (
$active && $mrc == CURLM_OK) {
   
//check for results and execute until everything is done

   
if (curl_multi_select($multi) == -1) {
       
//if it returns -1, wait a bit, but go forward anyways!
       
usleep(100);
    }
   
   
//do something with the return values
   
while(($info = curl_multi_info_read($multi)) !== false){
        if (
$info["result"] == CURLE_OK){
           
$content = curl_multi_getcontent($info["handle"]);
           
do_something($content);
        }
    }
    do { 
       
$mrc = curl_multi_exec($multi, $active); 
    } while (
$mrc == CURLM_CALL_MULTI_PERFORM);         
}
?>
up
-3
Anonymous
3 years ago
Since the docs are still lacking, here's an example of how to use the function. The following code will keep checking all active threads until one of them returns the HTTP 200 Ok status code, or simply end. On success, it will return the URL that worked.

<?php
$running
=null;
do {
   
curl_multi_exec($mh,$running);
   
$ready=curl_multi_select($mh); // this will pause the loop
   
if($ready>0){
        while(
$info=curl_multi_info_read($mh)){
           
$status=curl_getinfo($info['handle'],CURLINFO_HTTP_CODE);
            if(
$status==200){
               
$successUrl=curl_getinfo($info['handle'],CURLINFO_EFFECTIVE_URL);
                break
2;
            }
        }
    }
} while (
$running>0 && $ready!=-1);
?>

The question for the $ready variable is, if it will return the value before or after the timeout has occurred. From my tests it appears that it will return the value immediately, and only then pause the execution. That's because it's always zero the first time through the loop, even if the time limit is as high as 10sec. I've expected it to wait and only then return the value so that came unexpected to me.

As stated by someone else, it also doesn't seem to return the overall count of threads in the handle, but only that of the currently active ones.
To Top