Curl error handler

(PHP 4 >= 4.0.3, PHP 5, PHP 7, PHP 8)

(PHP 4 >= 4.0.3, PHP 5, PHP 7, PHP 8)

curl_errorВозвращает строку с описанием последней ошибки текущего сеанса

Описание

Список параметров

handle

Дескриптор cURL, полученный из curl_init().

Возвращаемые значения

Возвращает сообщение об ошибке или '' (пустую строку),
если ошибки не произошло.

Список изменений

Версия Описание
8.0.0 handle теперь ожидает экземпляр CurlHandle;
раньше, ожидался ресурс (resource).

Примеры

Пример #1 Пример использования curl_error()


<?php
// Создаём дескриптор curl к несуществующему адресу
$ch = curl_init('http://404.php.net/');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

if(

curl_exec($ch) === false)
{
echo
'Ошибка curl: ' . curl_error($ch);
}
else
{
echo
'Операция завершена без каких-либо ошибок';
}
// Закрываем дескриптор
curl_close($ch);
?>

patrick at ibuildings dot nl

9 years ago


If you want to fetch the error message, make sure you fetch it before you close the current cURL session or the error message will be reset to an empty string.

paul at paulmcgarry dot com

14 years ago


For a 404 response to actually trigger an error as the example seems to be trying to demonstrate the following option should be set:

curl_setopt($ch,CURLOPT_FAILONERROR,true);

As per http://curl.haxx.se/libcurl/c/libcurl-errors.html

CURLE_HTTP_RETURNED_ERROR (22)
This is returned if CURLOPT_FAILONERROR is set TRUE and the HTTP server returns an error code that is >= 400. (This error code was formerly known as CURLE_HTTP_NOT_FOUND.)


anrdaemon at freemail dot ru

3 years ago


curl_error is not a textual representation of curl_errno.
It's an actual error *message*.
If you want textual representation of error *code*, look for curl_strerror.

Anonymous

2 years ago


If you're using curl_multi and there's an error, curl_error() will remain empty until you've called curl_multi_info_read(). That function "pumps" the information inside the curl libraries to the point where curl_error() will return a useful string.

This should really be added to the documentation, because it's not at all obvious.


you can generate curl error after its execution

$url = 'http://example.com';

$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
if(curl_errno($ch)){
    echo 'Request Error:' . curl_error($ch);
}

and here are curl error code

if someone need more information about curl errors

<?php

    $error_codes=array(
    [1] => 'CURLE_UNSUPPORTED_PROTOCOL',
    [2] => 'CURLE_FAILED_INIT',
    [3] => 'CURLE_URL_MALFORMAT',
    [4] => 'CURLE_URL_MALFORMAT_USER',
    [5] => 'CURLE_COULDNT_RESOLVE_PROXY',
    [6] => 'CURLE_COULDNT_RESOLVE_HOST',
    [7] => 'CURLE_COULDNT_CONNECT',
    [8] => 'CURLE_FTP_WEIRD_SERVER_REPLY',
    [9] => 'CURLE_REMOTE_ACCESS_DENIED',
    [11] => 'CURLE_FTP_WEIRD_PASS_REPLY',
    [13] => 'CURLE_FTP_WEIRD_PASV_REPLY',
    [14]=>'CURLE_FTP_WEIRD_227_FORMAT',
    [15] => 'CURLE_FTP_CANT_GET_HOST',
    [17] => 'CURLE_FTP_COULDNT_SET_TYPE',
    [18] => 'CURLE_PARTIAL_FILE',
    [19] => 'CURLE_FTP_COULDNT_RETR_FILE',
    [21] => 'CURLE_QUOTE_ERROR',
    [22] => 'CURLE_HTTP_RETURNED_ERROR',
    [23] => 'CURLE_WRITE_ERROR',
    [25] => 'CURLE_UPLOAD_FAILED',
    [26] => 'CURLE_READ_ERROR',
    [27] => 'CURLE_OUT_OF_MEMORY',
    [28] => 'CURLE_OPERATION_TIMEDOUT',
    [30] => 'CURLE_FTP_PORT_FAILED',
    [31] => 'CURLE_FTP_COULDNT_USE_REST',
    [33] => 'CURLE_RANGE_ERROR',
    [34] => 'CURLE_HTTP_POST_ERROR',
    [35] => 'CURLE_SSL_CONNECT_ERROR',
    [36] => 'CURLE_BAD_DOWNLOAD_RESUME',
    [37] => 'CURLE_FILE_COULDNT_READ_FILE',
    [38] => 'CURLE_LDAP_CANNOT_BIND',
    [39] => 'CURLE_LDAP_SEARCH_FAILED',
    [41] => 'CURLE_FUNCTION_NOT_FOUND',
    [42] => 'CURLE_ABORTED_BY_CALLBACK',
    [43] => 'CURLE_BAD_FUNCTION_ARGUMENT',
    [45] => 'CURLE_INTERFACE_FAILED',
    [47] => 'CURLE_TOO_MANY_REDIRECTS',
    [48] => 'CURLE_UNKNOWN_TELNET_OPTION',
    [49] => 'CURLE_TELNET_OPTION_SYNTAX',
    [51] => 'CURLE_PEER_FAILED_VERIFICATION',
    [52] => 'CURLE_GOT_NOTHING',
    [53] => 'CURLE_SSL_ENGINE_NOTFOUND',
    [54] => 'CURLE_SSL_ENGINE_SETFAILED',
    [55] => 'CURLE_SEND_ERROR',
    [56] => 'CURLE_RECV_ERROR',
    [58] => 'CURLE_SSL_CERTPROBLEM',
    [59] => 'CURLE_SSL_CIPHER',
    [60] => 'CURLE_SSL_CACERT',
    [61] => 'CURLE_BAD_CONTENT_ENCODING',
    [62] => 'CURLE_LDAP_INVALID_URL',
    [63] => 'CURLE_FILESIZE_EXCEEDED',
    [64] => 'CURLE_USE_SSL_FAILED',
    [65] => 'CURLE_SEND_FAIL_REWIND',
    [66] => 'CURLE_SSL_ENGINE_INITFAILED',
    [67] => 'CURLE_LOGIN_DENIED',
    [68] => 'CURLE_TFTP_NOTFOUND',
    [69] => 'CURLE_TFTP_PERM',
    [70] => 'CURLE_REMOTE_DISK_FULL',
    [71] => 'CURLE_TFTP_ILLEGAL',
    [72] => 'CURLE_TFTP_UNKNOWNID',
    [73] => 'CURLE_REMOTE_FILE_EXISTS',
    [74] => 'CURLE_TFTP_NOSUCHUSER',
    [75] => 'CURLE_CONV_FAILED',
    [76] => 'CURLE_CONV_REQD',
    [77] => 'CURLE_SSL_CACERT_BADFILE',
    [78] => 'CURLE_REMOTE_FILE_NOT_FOUND',
    [79] => 'CURLE_SSH',
    [80] => 'CURLE_SSL_SHUTDOWN_FAILED',
    [81] => 'CURLE_AGAIN',
    [82] => 'CURLE_SSL_CRL_BADFILE',
    [83] => 'CURLE_SSL_ISSUER_ERROR',
    [84] => 'CURLE_FTP_PRET_FAILED',
    [84] => 'CURLE_FTP_PRET_FAILED',
    [85] => 'CURLE_RTSP_CSEQ_ERROR',
    [86] => 'CURLE_RTSP_SESSION_ERROR',
    [87] => 'CURLE_FTP_BAD_FILE_LIST',
    [88] => 'CURLE_CHUNK_FAILED');

    ?>

Содержание

  1. PHP: Error handling with cURL
  2. Using curl_errno to detect cURL errors.
  3. Throwing Exceptions.
  4. curl_errno
  5. Description
  6. Parameters
  7. Return Values
  8. Changelog
  9. Examples
  10. See Also
  11. User Contributed Notes 10 notes
  12. curl_error
  13. Description
  14. Parameters
  15. Return Values
  16. Changelog
  17. Examples
  18. See Also
  19. User Contributed Notes 4 notes
  20. Как отловить ошибки cURL в PHP
  21. Ответ 1
  22. Ответ 2
  23. Ответ 3
  24. Клиентская библиотека работы с URL
  25. User Contributed Notes 30 notes

PHP: Error handling with cURL

PHP’s cURL functions are extremely useful for sending HTTP requests.

Some examples of its usefulness.

  • Retrieving data from an external API.
  • Sending data to an external web service.
  • Checking to see if a HTTP resource exists.
  • Crawling / scraping web pages (logging into other websites with PHP).

Although you can easily request external content via the function file_get_contents, cURL is much more useful in the sense that it allows us to detect and handle certain HTTP errors.

Let’s take the following example.

As you can see, we have setup a very simple GET request that returns the contents of a website called example.com.

Unfortunately, this code doesn’t take into account the fact that the cURL request could fail. As a result, the request might fail without providing us with any details about what happened.

Using curl_errno to detect cURL errors.

This is where the curl_errno function comes in handy.

The curl_errno function will return the number 0 (zero) if the request was successful. In other words, it will return a “falsey” value if no error occurs. This is because PHP sees 0 as a false value in a boolean context.

This allows us to figure out whether or not our cURL request resulted in an error.

Take a look at the following example.

If an error occurs, then our script will print out the result of the curl_error function.

Throwing Exceptions.

In certain situations, you might want to throw an exception if a cURL request fails.

For this example, let us pretend that we have an object function called get.

As you can see, the function above will attempt to send a GET request to a given URL.

If all goes well, the function will return the contents of the URL.

However, if the request fails and a cURL error exists, PHP will throw an Exception.

This allows us to handle the request like so.

In the above piece of code, we are using a TRY-CATCH block.

If we do not want our application to continue after a failed HTTP request, we can omit the TRY-CATCH block and let our Exception Handler deal with it.

Источник

curl_errno

(PHP 4 >= 4.0.3, PHP 5, PHP 7, PHP 8)

curl_errno — Return the last error number

Description

Returns the error number for the last cURL operation.

Parameters

A cURL handle returned by curl_init() .

Return Values

Returns the error number or 0 (zero) if no error occurred.

Changelog

Version Description
8.0.0 handle expects a CurlHandle instance now; previously, a resource was expected.

Examples

Example #1 curl_errno() example

// Create a curl handle to a non-existing location
$ch = curl_init ( ‘http://404.php.net/’ );

// Execute
curl_setopt ( $ch , CURLOPT_RETURNTRANSFER , true );
curl_exec ( $ch );

// Check if any error occurred
if( curl_errno ( $ch ))
<
echo ‘Curl error: ‘ . curl_error ( $ch );
>

// Close handle
curl_close ( $ch );
?>

See Also

  • curl_error() — Return a string containing the last error for the current session
  • » Curl error codes

User Contributed Notes 10 notes

if someone need more information about curl errors
=array(
[ 1 ] => ‘CURLE_UNSUPPORTED_PROTOCOL’ ,
[ 2 ] => ‘CURLE_FAILED_INIT’ ,
[ 3 ] => ‘CURLE_URL_MALFORMAT’ ,
[ 4 ] => ‘CURLE_URL_MALFORMAT_USER’ ,
[ 5 ] => ‘CURLE_COULDNT_RESOLVE_PROXY’ ,
[ 6 ] => ‘CURLE_COULDNT_RESOLVE_HOST’ ,
[ 7 ] => ‘CURLE_COULDNT_CONNECT’ ,
[ 8 ] => ‘CURLE_FTP_WEIRD_SERVER_REPLY’ ,
[ 9 ] => ‘CURLE_REMOTE_ACCESS_DENIED’ ,
[ 11 ] => ‘CURLE_FTP_WEIRD_PASS_REPLY’ ,
[ 13 ] => ‘CURLE_FTP_WEIRD_PASV_REPLY’ ,
[ 14 ]=> ‘CURLE_FTP_WEIRD_227_FORMAT’ ,
[ 15 ] => ‘CURLE_FTP_CANT_GET_HOST’ ,
[ 17 ] => ‘CURLE_FTP_COULDNT_SET_TYPE’ ,
[ 18 ] => ‘CURLE_PARTIAL_FILE’ ,
[ 19 ] => ‘CURLE_FTP_COULDNT_RETR_FILE’ ,
[ 21 ] => ‘CURLE_QUOTE_ERROR’ ,
[ 22 ] => ‘CURLE_HTTP_RETURNED_ERROR’ ,
[ 23 ] => ‘CURLE_WRITE_ERROR’ ,
[ 25 ] => ‘CURLE_UPLOAD_FAILED’ ,
[ 26 ] => ‘CURLE_READ_ERROR’ ,
[ 27 ] => ‘CURLE_OUT_OF_MEMORY’ ,
[ 28 ] => ‘CURLE_OPERATION_TIMEDOUT’ ,
[ 30 ] => ‘CURLE_FTP_PORT_FAILED’ ,
[ 31 ] => ‘CURLE_FTP_COULDNT_USE_REST’ ,
[ 33 ] => ‘CURLE_RANGE_ERROR’ ,
[ 34 ] => ‘CURLE_HTTP_POST_ERROR’ ,
[ 35 ] => ‘CURLE_SSL_CONNECT_ERROR’ ,
[ 36 ] => ‘CURLE_BAD_DOWNLOAD_RESUME’ ,
[ 37 ] => ‘CURLE_FILE_COULDNT_READ_FILE’ ,
[ 38 ] => ‘CURLE_LDAP_CANNOT_BIND’ ,
[ 39 ] => ‘CURLE_LDAP_SEARCH_FAILED’ ,
[ 41 ] => ‘CURLE_FUNCTION_NOT_FOUND’ ,
[ 42 ] => ‘CURLE_ABORTED_BY_CALLBACK’ ,
[ 43 ] => ‘CURLE_BAD_FUNCTION_ARGUMENT’ ,
[ 45 ] => ‘CURLE_INTERFACE_FAILED’ ,
[ 47 ] => ‘CURLE_TOO_MANY_REDIRECTS’ ,
[ 48 ] => ‘CURLE_UNKNOWN_TELNET_OPTION’ ,
[ 49 ] => ‘CURLE_TELNET_OPTION_SYNTAX’ ,
[ 51 ] => ‘CURLE_PEER_FAILED_VERIFICATION’ ,
[ 52 ] => ‘CURLE_GOT_NOTHING’ ,
[ 53 ] => ‘CURLE_SSL_ENGINE_NOTFOUND’ ,
[ 54 ] => ‘CURLE_SSL_ENGINE_SETFAILED’ ,
[ 55 ] => ‘CURLE_SEND_ERROR’ ,
[ 56 ] => ‘CURLE_RECV_ERROR’ ,
[ 58 ] => ‘CURLE_SSL_CERTPROBLEM’ ,
[ 59 ] => ‘CURLE_SSL_CIPHER’ ,
[ 60 ] => ‘CURLE_SSL_CACERT’ ,
[ 61 ] => ‘CURLE_BAD_CONTENT_ENCODING’ ,
[ 62 ] => ‘CURLE_LDAP_INVALID_URL’ ,
[ 63 ] => ‘CURLE_FILESIZE_EXCEEDED’ ,
[ 64 ] => ‘CURLE_USE_SSL_FAILED’ ,
[ 65 ] => ‘CURLE_SEND_FAIL_REWIND’ ,
[ 66 ] => ‘CURLE_SSL_ENGINE_INITFAILED’ ,
[ 67 ] => ‘CURLE_LOGIN_DENIED’ ,
[ 68 ] => ‘CURLE_TFTP_NOTFOUND’ ,
[ 69 ] => ‘CURLE_TFTP_PERM’ ,
[ 70 ] => ‘CURLE_REMOTE_DISK_FULL’ ,
[ 71 ] => ‘CURLE_TFTP_ILLEGAL’ ,
[ 72 ] => ‘CURLE_TFTP_UNKNOWNID’ ,
[ 73 ] => ‘CURLE_REMOTE_FILE_EXISTS’ ,
[ 74 ] => ‘CURLE_TFTP_NOSUCHUSER’ ,
[ 75 ] => ‘CURLE_CONV_FAILED’ ,
[ 76 ] => ‘CURLE_CONV_REQD’ ,
[ 77 ] => ‘CURLE_SSL_CACERT_BADFILE’ ,
[ 78 ] => ‘CURLE_REMOTE_FILE_NOT_FOUND’ ,
[ 79 ] => ‘CURLE_SSH’ ,
[ 80 ] => ‘CURLE_SSL_SHUTDOWN_FAILED’ ,
[ 81 ] => ‘CURLE_AGAIN’ ,
[ 82 ] => ‘CURLE_SSL_CRL_BADFILE’ ,
[ 83 ] => ‘CURLE_SSL_ISSUER_ERROR’ ,
[ 84 ] => ‘CURLE_FTP_PRET_FAILED’ ,
[ 84 ] => ‘CURLE_FTP_PRET_FAILED’ ,
[ 85 ] => ‘CURLE_RTSP_CSEQ_ERROR’ ,
[ 86 ] => ‘CURLE_RTSP_SESSION_ERROR’ ,
[ 87 ] => ‘CURLE_FTP_BAD_FILE_LIST’ ,
[ 88 ] => ‘CURLE_CHUNK_FAILED’ );

Источник

curl_error

(PHP 4 >= 4.0.3, PHP 5, PHP 7, PHP 8)

curl_error — Return a string containing the last error for the current session

Description

Returns a clear text error message for the last cURL operation.

Parameters

A cURL handle returned by curl_init() .

Return Values

Returns the error message or » (the empty string) if no error occurred.

Changelog

Version Description
8.0.0 handle expects a CurlHandle instance now; previously, a resource was expected.

Examples

Example #1 curl_error() example

// Create a curl handle to a non-existing location
$ch = curl_init ( ‘http://404.php.net/’ );
curl_setopt ( $ch , CURLOPT_RETURNTRANSFER , true );

if( curl_exec ( $ch ) === false )
<
echo ‘Curl error: ‘ . curl_error ( $ch );
>
else
<
echo ‘Operation completed without any errors’ ;
>

// Close handle
curl_close ( $ch );
?>

See Also

User Contributed Notes 4 notes

For a 404 response to actually trigger an error as the example seems to be trying to demonstrate the following option should be set:

CURLE_HTTP_RETURNED_ERROR (22)
This is returned if CURLOPT_FAILONERROR is set TRUE and the HTTP server returns an error code that is >= 400. (This error code was formerly known as CURLE_HTTP_NOT_FOUND.)

If you’re using curl_multi and there’s an error, curl_error() will remain empty until you’ve called curl_multi_info_read(). That function «pumps» the information inside the curl libraries to the point where curl_error() will return a useful string.

This should really be added to the documentation, because it’s not at all obvious.

Источник

Как отловить ошибки cURL в PHP

Я использую функции PHP curl для отправки данных на веб-сервер с моей локальной машины. Мой код выглядит следующим образом:

curl_setopt($c, CURLOPT_URL, $url);

curl_setopt($c, CURLOPT_RETURNTRANSFER, true);

curl_setopt($c, CURLOPT_POST, true);

curl_setopt($c, CURLOPT_POSTFIELDS, $data);

if (curl_exec($c) === false) <

К сожалению, я не могу поймать ни одной ошибки типа 404, 500 или сетевого уровня. Как же мне узнать, что данные не были размещены или получены с удаленного сервера?

Ответ 1

Вы можете использовать функцию curl_error(), чтобы определить, произошла ли какая-то ошибка. Например:

curl_setopt($ch, CURLOPT_URL, $your_url);

curl_setopt($ch, CURLOPT_FAILONERROR, true); // Требуется для того, чтобы коды ошибок HTTP сообщались через наш вызов к curl_error($ch)

// TODO — Обработать ошибку cURL соответствующим образом

Ответ 2

Если CURLOPT_FAILONERROR равно false, ошибки http не будут вызывать ошибок curl.

header(‘HTTP/1.1 503 Service Temporarily Unavailable’);

curl_setopt($ch, CURLOPT_FAILONERROR, true);

$http_status = curl_getinfo($ch, CURLINFO_HTTP_CODE);

echo «HTTP Status == 503
«;

echo «Curl Errno returned $curl_errno
«;

Ответ 3

Вы можете сгенерировать ошибку curl после его выполнения:

curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

echo ‘Request Error:’ . curl_error($ch);

И вот коды ошибок curl:

если кому-то нужна дополнительная информация об ошибках curl

Источник

Клиентская библиотека работы с URL

User Contributed Notes 30 notes

I wrote the following to see if a submitted URL has a valid http response code and also if it responds quickly.

Use the code like this:

= http_response ( $url ); // returns true only if http response code ?>

The second argument is optional, and it allows you to check for a specific response code

( $url , ‘400’ ); // returns true if http status is 400
?>

The third allows you to specify how long you are willing to wait for a response.

( $url , ‘200’ , 3 ); // returns true if the response takes less than 3 seconds and the response code is 200
?>

function http_response ( $url , $status = null , $wait = 3 )
<
$time = microtime ( true );
$expire = $time + $wait ;

// we fork the process so we don’t have to wait for a timeout
$pid = pcntl_fork ();
if ( $pid == — 1 ) <
die( ‘could not fork’ );
> else if ( $pid ) <
// we are the parent
$ch = curl_init ();
curl_setopt ( $ch , CURLOPT_URL , $url );
curl_setopt ( $ch , CURLOPT_HEADER , TRUE );
curl_setopt ( $ch , CURLOPT_NOBODY , TRUE ); // remove body
curl_setopt ( $ch , CURLOPT_RETURNTRANSFER , TRUE );
$head = curl_exec ( $ch );
$httpCode = curl_getinfo ( $ch , CURLINFO_HTTP_CODE );
curl_close ( $ch );

if( $status === null )
<
if( $httpCode 400 )
<
return TRUE ;
>
else
<
return FALSE ;
>
>
elseif( $status == $httpCode )
<
return TRUE ;
>

return FALSE ;
pcntl_wait ( $status ); //Protect against Zombie children
> else <
// we are the child
while( microtime ( true ) $expire )
<
sleep ( 0.5 );
>
return FALSE ;
>
>
?>

Hope this example helps. It is not 100% tested, so any feedback [sent directly to me by email] is appreciated.

I needed to use cURL in a php script to download data using not only SSL for the server authentication but also for client authentication.
On a default install of Fedora, setting up the proper cURL parameters, I would get an error:

$ php curl.php
Peer certificate cannot be authenticated with known CA certificates

The data on http://curl.haxx.se/docs/sslcerts.html was most useful. Indeed, toward to bottom it tells you to add a missing link inside /etc/pki/nssdb to use the ca-bundle.crt file. You do it so:

# cd /etc/pki/nssdb
# ln -s /usr/lib64/libnssckbi.so libnssckbi.so

Now you can do client authentication, provided you have your certificate handy with:

= » [. ] » ;
$tuCurl = curl_init ();
curl_setopt ( $tuCurl , CURLOPT_URL , «https://example.com/path/for/soap/url/» );
curl_setopt ( $tuCurl , CURLOPT_PORT , 443 );
curl_setopt ( $tuCurl , CURLOPT_VERBOSE , 0 );
curl_setopt ( $tuCurl , CURLOPT_HEADER , 0 );
curl_setopt ( $tuCurl , CURLOPT_SSLVERSION , 3 );
curl_setopt ( $tuCurl , CURLOPT_SSLCERT , getcwd () . «/client.pem» );
curl_setopt ( $tuCurl , CURLOPT_SSLKEY , getcwd () . «/keyout.pem» );
curl_setopt ( $tuCurl , CURLOPT_CAINFO , getcwd () . «/ca.pem» );
curl_setopt ( $tuCurl , CURLOPT_POST , 1 );
curl_setopt ( $tuCurl , CURLOPT_SSL_VERIFYPEER , 1 );
curl_setopt ( $tuCurl , CURLOPT_RETURNTRANSFER , 1 );
curl_setopt ( $tuCurl , CURLOPT_POSTFIELDS , $data );
curl_setopt ( $tuCurl , CURLOPT_HTTPHEADER , array( «Content-Type: text/xml» , «SOAPAction: »/soap/action/query»» , «Content-length: » . strlen ( $data )));

$tuData = curl_exec ( $tuCurl );
if(! curl_errno ( $tuCurl )) <
$info = curl_getinfo ( $tuCurl );
echo ‘Took ‘ . $info [ ‘total_time’ ] . ‘ seconds to send a request to ‘ . $info [ ‘url’ ];
> else <
echo ‘Curl error: ‘ . curl_error ( $tuCurl );
>

curl_close ( $tuCurl );
echo $tuData ;
?>

In this example: http://php.net/manual/en/book.curl.php#102885 by «frank at interactinet dot com»

There’s a small bug in

elseif( $status == $httpCode )
<
return TRUE ;
>

return FALSE ;
pcntl_wait ( $status ); //Protect against Zombie children
> else <
// we are the child
while( microtime ( true ) $expire )

?>

The code will immediately leave the function at the `return`, and pcntl_wait() will NEVER be executed, under any circumstances.

I can’t see any other issues with this function however.

Hey I modified script for php 5. Also I add support server auth. and fixed some little bugs on the script.

[EDIT BY danbrown AT php DOT net: Original was written by (unlcuky13 AT gmail DOT com) on 19-APR-09. The following note was included:
Below is the my way of using through PHP 5 objecte oriented encapsulation to make thing easier.]

class mycurl <
protected $_useragent = ‘Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1’ ;
protected $_url ;
protected $_followlocation ;
protected $_timeout ;
protected $_maxRedirects ;
protected $_cookieFileLocation = ‘./cookie.txt’ ;
protected $_post ;
protected $_postFields ;
protected $_referer = «http://www.google.com» ;

protected $_session ;
protected $_webpage ;
protected $_includeHeader ;
protected $_noBody ;
protected $_status ;
protected $_binaryTransfer ;
public $authentication = 0 ;
public $auth_name = » ;
public $auth_pass = » ;

public function useAuth ( $use ) <
$this -> authentication = 0 ;
if( $use == true ) $this -> authentication = 1 ;
>

public function setName ( $name ) <
$this -> auth_name = $name ;
>
public function setPass ( $pass ) <
$this -> auth_pass = $pass ;
>

public function __construct ( $url , $followlocation = true , $timeOut = 30 , $maxRedirecs = 4 , $binaryTransfer = false , $includeHeader = false , $noBody = false )
<
$this -> _url = $url ;
$this -> _followlocation = $followlocation ;
$this -> _timeout = $timeOut ;
$this -> _maxRedirects = $maxRedirecs ;
$this -> _noBody = $noBody ;
$this -> _includeHeader = $includeHeader ;
$this -> _binaryTransfer = $binaryTransfer ;

$this -> _cookieFileLocation = dirname ( __FILE__ ). ‘/cookie.txt’ ;

public function setReferer ( $referer ) <
$this -> _referer = $referer ;
>

public function setCookiFileLocation ( $path )
<
$this -> _cookieFileLocation = $path ;
>

public function setPost ( $postFields )
<
$this -> _post = true ;
$this -> _postFields = $postFields ;
>

public function setUserAgent ( $userAgent )
<
$this -> _useragent = $userAgent ;
>

public function createCurl ( $url = ‘nul’ )
<
if( $url != ‘nul’ ) <
$this -> _url = $url ;
>

curl_setopt ( $s , CURLOPT_URL , $this -> _url );
curl_setopt ( $s , CURLOPT_HTTPHEADER ,array( ‘Expect:’ ));
curl_setopt ( $s , CURLOPT_TIMEOUT , $this -> _timeout );
curl_setopt ( $s , CURLOPT_MAXREDIRS , $this -> _maxRedirects );
curl_setopt ( $s , CURLOPT_RETURNTRANSFER , true );
curl_setopt ( $s , CURLOPT_FOLLOWLOCATION , $this -> _followlocation );
curl_setopt ( $s , CURLOPT_COOKIEJAR , $this -> _cookieFileLocation );
curl_setopt ( $s , CURLOPT_COOKIEFILE , $this -> _cookieFileLocation );

if( $this -> authentication == 1 ) <
curl_setopt ( $s , CURLOPT_USERPWD , $this -> auth_name . ‘:’ . $this -> auth_pass );
>
if( $this -> _post )
<
curl_setopt ( $s , CURLOPT_POST , true );
curl_setopt ( $s , CURLOPT_POSTFIELDS , $this -> _postFields );

if( $this -> _includeHeader )
<
curl_setopt ( $s , CURLOPT_HEADER , true );
>

if( $this -> _noBody )
<
curl_setopt ( $s , CURLOPT_NOBODY , true );
>
/*
if($this->_binary)
<
curl_setopt($s,CURLOPT_BINARYTRANSFER,true);
>
*/
curl_setopt ( $s , CURLOPT_USERAGENT , $this -> _useragent );
curl_setopt ( $s , CURLOPT_REFERER , $this -> _referer );

$this -> _webpage = curl_exec ( $s );
$this -> _status = curl_getinfo ( $s , CURLINFO_HTTP_CODE );
curl_close ( $s );

public function getHttpStatus ()
<
return $this -> _status ;
>

public function __tostring () <
return $this -> _webpage ;
>
>
?>

[EDIT BY danbrown AT php DOT net: Contains a bugfix supplied by «roetsch.beni at googlemail (dot) com» on 02-AUG-09, with the following note: «Fixes the bugfix: 417 bug at lighthttp server.»]

CURL failed with PHP5.3 and Apache2.2.X on my Windows 7 machine.

It turns out that it’s not enough to copy the two dll’s mentioned (libeay32 and sslea32) from the php folder into your system32 folder. You HAVE TO UNBLOCK THESE TWO FILES.

Right click the file, select unblock, for each one. Then restart Apache.

Another very handy security feature added into Windows.

Sharing is caring, handles included.

$user_agent = ‘Mozilla HotFox 1.0’ ;

$ch = curl_init ();
curl_setopt ( $ch , CURLOPT_URL , $url_one . $url_two );
curl_setopt ( $ch , CURLOPT_USERAGENT , $user_agent );
curl_setopt ( $ch , CURLOPT_RETURNTRANSFER , true );
curl_setopt ( $ch , CURLOPT_FOLLOWLOCATION , 1 );
curl_setopt ( $ch , CURLOPT_HEADER , 0 );
curl_setopt ( $ch , CURLOPT_NOBODY , 0 );
curl_setopt ( $ch , CURLOPT_TIMEOUT , 30 );
$res = curl_exec ( $ch );
curl_close ( $ch );

$url_two = «lazyphp.net» ;
$url_one = «» ;
$res_two = curl_exec ( $ch );
curl_close ( $ch );

Here you have a function that I use to get the content of a URL using cURL:

function getUrlContent($url) <
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_USERAGENT, ‘Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; .NET CLR 1.1.4322)’);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 5);
curl_setopt($ch, CURLOPT_TIMEOUT, 5);
$data = curl_exec($ch);
$httpcode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
curl_close($ch);
return ($httpcode>=200 && $httpcode

In order to use curl with secure sites you will need a ca-bundle.crt file; here’s a PHP script I’ve written which creates a fresh ca-bundle:
http://www.gknw.net/php/phpscripts/mk-ca-bundle.php
I’ve also written scripts in other languages, f.e. the Perl one which ships now with curl distributions:
http://curl.haxx.se/lxr/source/lib/mk-ca-bundle.pl
and also a Win32 WSH script if you prefer that:
http://www.gknw.net/vb/scripts/mk-ca-bundle.vbs

You can use this class for fast entry

class cURL <
var $headers ;
var $user_agent ;
var $compression ;
var $cookie_file ;
var $proxy ;
function cURL ( $cookies = TRUE , $cookie = ‘cookies.txt’ , $compression = ‘gzip’ , $proxy = » ) <
$this -> headers [] = ‘Accept: image/gif, image/x-bitmap, image/jpeg, image/pjpeg’ ;
$this -> headers [] = ‘Connection: Keep-Alive’ ;
$this -> headers [] = ‘Content-type: application/x-www-form-urlencoded;charset=UTF-8’ ;
$this -> user_agent = ‘Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1; .NET CLR 1.0.3705; .NET CLR 1.1.4322; Media Center PC 4.0)’ ;
$this -> compression = $compression ;
$this -> proxy = $proxy ;
$this -> cookies = $cookies ;
if ( $this -> cookies == TRUE ) $this -> cookie ( $cookie );
>
function cookie ( $cookie_file ) <
if ( file_exists ( $cookie_file )) <
$this -> cookie_file = $cookie_file ;
> else <
fopen ( $cookie_file , ‘w’ ) or $this -> error ( ‘The cookie file could not be opened. Make sure this directory has the correct permissions’ );
$this -> cookie_file = $cookie_file ;
fclose ( $this -> cookie_file );
>
>
function get ( $url ) <
$process = curl_init ( $url );
curl_setopt ( $process , CURLOPT_HTTPHEADER , $this -> headers );
curl_setopt ( $process , CURLOPT_HEADER , 0 );
curl_setopt ( $process , CURLOPT_USERAGENT , $this -> user_agent );
if ( $this -> cookies == TRUE ) curl_setopt ( $process , CURLOPT_COOKIEFILE , $this -> cookie_file );
if ( $this -> cookies == TRUE ) curl_setopt ( $process , CURLOPT_COOKIEJAR , $this -> cookie_file );
curl_setopt ( $process , CURLOPT_ENCODING , $this -> compression );
curl_setopt ( $process , CURLOPT_TIMEOUT , 30 );
if ( $this -> proxy ) curl_setopt ( $process , CURLOPT_PROXY , $this -> proxy );
curl_setopt ( $process , CURLOPT_RETURNTRANSFER , 1 );
curl_setopt ( $process , CURLOPT_FOLLOWLOCATION , 1 );
$return = curl_exec ( $process );
curl_close ( $process );
return $return ;
>
function post ( $url , $data ) <
$process = curl_init ( $url );
curl_setopt ( $process , CURLOPT_HTTPHEADER , $this -> headers );
curl_setopt ( $process , CURLOPT_HEADER , 1 );
curl_setopt ( $process , CURLOPT_USERAGENT , $this -> user_agent );
if ( $this -> cookies == TRUE ) curl_setopt ( $process , CURLOPT_COOKIEFILE , $this -> cookie_file );
if ( $this -> cookies == TRUE ) curl_setopt ( $process , CURLOPT_COOKIEJAR , $this -> cookie_file );
curl_setopt ( $process , CURLOPT_ENCODING , $this -> compression );
curl_setopt ( $process , CURLOPT_TIMEOUT , 30 );
if ( $this -> proxy ) curl_setopt ( $process , CURLOPT_PROXY , $this -> proxy );
curl_setopt ( $process , CURLOPT_POSTFIELDS , $data );
curl_setopt ( $process , CURLOPT_RETURNTRANSFER , 1 );
curl_setopt ( $process , CURLOPT_FOLLOWLOCATION , 1 );
curl_setopt ( $process , CURLOPT_POST , 1 );
$return = curl_exec ( $process );
curl_close ( $process );
return $return ;
>
function error ( $error ) <
echo «

» ;
die;
>
>
$cc = new cURL ();
$cc -> get ( ‘http://www.example.com’ );
$cc -> post ( ‘http://www.example.com’ , ‘foo=bar’ );
?>

[EDIT BY danbrown AT php DOT net: Includes a bugfix provided by «Anonymous» on 01-Dec-2008 @ 06:52. Also replaced real URL with example.com as per RFC 2606.]

[EDIT BY danbrown AT php DOT net: Includes a bugfix provided by (manuel AT rankone DOT ch) on 24-NOV-09 to properly reference cURL initialization.]

Источник

PHP’s cURL functions are extremely useful for sending HTTP requests.

Some examples of its usefulness.

  • Retrieving data from an external API.
  • Sending data to an external web service.
  • Checking to see if a HTTP resource exists.
  • Crawling / scraping web pages (logging into other websites with PHP).

Although you can easily request external content via the function file_get_contents, cURL is much more useful in the sense that it allows us to detect and handle certain HTTP errors.

Let’s take the following example.

$url = 'http://example.com';
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
echo $result;

As you can see, we have setup a very simple GET request that returns the contents of a website called example.com.

Unfortunately, this code doesn’t take into account the fact that the cURL request could fail. As a result, the request might fail without providing us with any details about what happened.

Using curl_errno to detect cURL errors.

This is where the curl_errno function comes in handy.

The curl_errno function will return the number 0 (zero) if the request was successful. In other words, it will return a “falsey” value if no error occurs. This is because PHP sees 0 as a false value in a boolean context.

This allows us to figure out whether or not our cURL request resulted in an error.

Take a look at the following example.

$url = 'http://example.com';

$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
if(curl_errno($ch)){
    echo 'Request Error:' . curl_error($ch);
}

If an error occurs, then our script will print out the result of the curl_error function.

Throwing Exceptions.

In certain situations, you might want to throw an exception if a cURL request fails.

For this example, let us pretend that we have an object function called get.

/**
 * Send a GET request to a URL.
 * 
 * @param string $url
 * @return string
 * @throws Exception If cURL request fails.
 */
public function get($url){
    $ch = curl_init($url);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    $result = curl_exec($ch);
    if(curl_errno($ch)){
        throw new Exception(curl_error($ch));
    }
    return $result;
}

As you can see, the function above will attempt to send a GET request to a given URL.

If all goes well, the function will return the contents of the URL.

However, if the request fails and a cURL error exists, PHP will throw an Exception.

This allows us to handle the request like so.

try{
    $object->get('http://test.com');
} catch(Exception $e){
    //do something with the exception you caught
}

In the above piece of code, we are using a TRY-CATCH block.

If we do not want our application to continue after a failed HTTP request, we can omit the TRY-CATCH block and let our Exception Handler deal with it.

    Table of contents

  • Using a try/catch with cURL in PHP
  • How to catch cURL errors in php
  • PHP: Error handling with cURL
  • PHP try…catch
  • PHP Try Catch: Basics & Advanced PHP Exception Handling Tutorial
  • CURL try catch problem
  • PHP Try Catch Example: Exception & Error Handling Tutorial

Using a try/catch with cURL in PHP

$options[CURLOPT_URL] = 'https://[domain]/test.htm';

$options[CURLOPT_PORT] = 443;
$options[CURLOPT_FRESH_CONNECT] = true;
$options[CURLOPT_FOLLOWLOCATION] = false;
$options[CURLOPT_FAILONERROR] = true;
$options[CURLOPT_RETURNTRANSFER] = true;
$options[CURLOPT_TIMEOUT] = 10;

// Preset $response var to false and output
$fb = "";
$response = "false";
echo '<p class="response1">'.$response.'</p>';

try {
    $curl = curl_init();
    echo curl_setopt_array($curl, $options);
    // If curl request returns a value, I set it to the var here. 
    // If the file isn't found (server offline), the try/catch fails and var should stay as false.
    $fb = curl_exec($curl);
    curl_close($curl);
}
catch(Exception $e){
    throw new Exception("Invalid URL",0,$e);
}

if($fb == "true" || $fb == "false") {
    echo '<p class="response2">'.$fb.'</p>';
    $response = $fb;
}

// If cURL was successful, $response should now be true, otherwise it will have stayed false.
echo '<p class="response3">'.$response.'</p>';
$options[CURLOPT_URL] = 'https://[domain]/test.htm';

$options[CURLOPT_PORT] = 443;
$options[CURLOPT_FRESH_CONNECT] = true;
$options[CURLOPT_FOLLOWLOCATION] = false;
$options[CURLOPT_FAILONERROR] = true;
$options[CURLOPT_RETURNTRANSFER] = true; // curl_exec will not return true if you use this, it will instead return the request body
$options[CURLOPT_TIMEOUT] = 10;

// Preset $response var to false and output
$fb = "";
$response = false;// don't quote booleans
echo '<p class="response1">'.$response.'</p>';

$curl = curl_init();
curl_setopt_array($curl, $options);
// If curl request returns a value, I set it to the var here. 
// If the file isn't found (server offline), the try/catch fails and var should stay as false.
$fb = curl_exec($curl);
curl_close($curl);

if($fb !== false) {
    echo '<p class="response2">'.$fb.'</p>';
    $response = $fb;
}

// If cURL was successful, $response should now be true, otherwise it will have stayed false.
echo '<p class="response3">'.$response.'</p>';

How to catch cURL errors in php

<?php

$url = 'https://hackthestuff.com/api/request';

$data = [
    'name' => 'Hackthestuff',
    'email' => '[email protected]'
];

$ch = curl_init();

curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, $data);
// required for HTTP error codes to be reported
curl_setopt($ch, CURLOPT_FAILONERROR, true);

$result = curl_exec($ch);

if (curl_errno($ch)) {
    $error_msg = curl_error($ch);
}
curl_close($ch);

if (isset($error_msg)) {
    // echo($error_msg);
}

PHP: Error handling with cURL

$url = 'http://example.com';
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
echo $result;
$url = 'http://example.com';

$ch = curl_init($url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = curl_exec($ch);
if(curl_errno($ch)){
    echo 'Request Error:' . curl_error($ch);
}
/**
 * Send a GET request to a URL.
 * 
 * @param string $url
 * @return string
 * @throws Exception If cURL request fails.
 */
public function get($url){
    $ch = curl_init($url);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    $result = curl_exec($ch);
    if(curl_errno($ch)){
        throw new Exception(curl_error($ch));
    }
    return $result;
}
try{
    $object->get('http://test.com');
} catch(Exception $e){
    //do something with the exception you caught
}

PHP try…catch

.wp-block-code {
	border: 0;
	padding: 0;
}

.wp-block-code > div {
	overflow: auto;
}

.shcb-language {
	border: 0;
	clip: rect(1px, 1px, 1px, 1px);
	-webkit-clip-path: inset(50%);
	clip-path: inset(50%);
	height: 1px;
	margin: -1px;
	overflow: hidden;
	padding: 0;
	position: absolute;
	width: 1px;
	word-wrap: normal;
	word-break: normal;
}

.hljs {
	box-sizing: border-box;
}

.hljs.shcb-code-table {
	display: table;
	width: 100%;
}

.hljs.shcb-code-table > .shcb-loc {
	color: inherit;
	display: table-row;
	width: 100%;
}

.hljs.shcb-code-table .shcb-loc > span {
	display: table-cell;
}

.wp-block-code code.hljs:not(.shcb-wrap-lines) {
	white-space: pre;
}

.wp-block-code code.hljs.shcb-wrap-lines {
	white-space: pre-wrap;
}

.hljs.shcb-line-numbers {
	border-spacing: 0;
	counter-reset: line;
}

.hljs.shcb-line-numbers > .shcb-loc {
	counter-increment: line;
}

.hljs.shcb-line-numbers .shcb-loc > span {
	padding-left: 0.75em;
}

.hljs.shcb-line-numbers .shcb-loc::before {
	border-right: 1px solid #ddd;
	content: counter(line);
	display: table-cell;
	padding: 0 0.75em;
	text-align: right;
	-webkit-user-select: none;
	-moz-user-select: none;
	-ms-user-select: none;
	user-select: none;
	white-space: nowrap;
	width: 1%;
}<?php

try {
	// perform some task
} catch (Exception $ex) {
	// jump to this part
	// if an exception occurred
}
Code language: HTML, XML (xml)
<?php

$data = [];

$f = fopen('data.csv', 'r');

do {
	$row = fgetcsv($f);
	$data[] = $row;
} while ($row);

fclose($f);Code language: HTML, XML (xml)
PHP Warning:  fopen(data.csv): failed to open stream: No such file or directory in ... on line 5Code language: plaintext (plaintext)
<?php

$data = [];

$f = fopen('data1.csv', 'r');

if (!$f) {
	echo 'The file is not accessible.';
	exit;
}

do {
	$row = fgetcsv($f);
	if ($row === null) {
		echo 'The stream is invalid.';
		exit;
	}

	if ($row === false) {
		echo 'Other errors occurred.';
		exit;
	}

	$data[] = $row;
} while ($row);

// close the file
if (!$f) {
	fclose($f);
}

print_r($data);Code language: HTML, XML (xml)
<?php

$data = [];

try {
	$f = fopen('data.csv', 'r');

	do {
		$row = fgetcsv($f);
		$data[] = $row;
	} while ($row);

	fclose($f);
} catch (Exception $ex) {
	echo $ex->getMessage();
}
Code language: HTML, XML (xml)
<?php

try {
	//code...
} catch (Exception1 $ex1) {
	// handle exception 1
} catch (Exception2 $ex2) {
	// handle exception 2
} catch (Exception1 $ex3) {
	// handle exception 3
}
...Code language: HTML, XML (xml)
<?php

try {
	//code...
} catch (Exception1 | Exception2 $ex12) {
	// handle exception 1 & 2
} catch (Exception3 $ex3) {
	// handle exception 3
}Code language: HTML, XML (xml)
<?php

try {
	//code...

} catch (Exception) {
	// handle exception
}
Code language: HTML, XML (xml)

PHP Try Catch: Basics & Advanced PHP Exception Handling Tutorial

try {
    // run your code here
}
catch (exception $e) {
    //code to handle the exception
}
finally {
    //optional code that always runs
}
try {
    // run your code here
}
catch (Exception $e) {
    echo $e->getMessage();
}
catch (InvalidArgumentException $e) {
    echo $e->getMessage();
}
try {
    print "this is our try block n";
    throw new Exception();
} catch (Exception $e) {
    print "something went wrong, caught yah! n";
} finally {
    print "this part is always executed n";
}
class DivideByZeroException extends Exception {};
class DivideByZeroException extends Exception {};
class DivideByNegativeException extends Exception {};

function process_divide($denominator)
{
    try
    {
        if ($denominator == 0)
        {
            throw new DivideByZeroException();
        }
        else if ($denominator < 0)
        {
            throw new DivideByNegativeException();
        }
        else
        {
            echo 100 / $denominator;
        }
    }
    catch (DivideByZeroException $ex)
    {
        echo "Divide by zero exception!";
    }
    catch (DivideByNegativeException $ex)
    {
        echo "Divide by negative number exception!";
    }
    catch (Exception $x)
    {
        echo "UNKNOWN EXCEPTION!";
    }
}
function our_global_exception_handler($exception) {
    //this code should log the exception to disk and an error tracking system
    echo "Exception:" . $exception->getMessage();
}

set_exception_handler(‘our_global_exception_handler’);
require_once(DIR.'/vendor/autoload.php');
use MonologLogger;
use MonologHandlerStreamHandler;

$logger = new Logger('channel-name');
$logger->pushHandler(new StreamHandler(DIR.'/app.log', Logger::DEBUG));

try {
    // Code does some stuff
    // debug logging statement
    $logger->info('This is a log! ^_^ ');
}
catch (Exception $ex) {
    $logger->error('Oh no an exception happened! ');
}
// connect to MySQL
$conn = new PDO('mysql:host=localhost;dbname=stackifydb;charset=utf8mb4', 'username', 'password');
//PDO error mode to exception
$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);

CURL try catch problem

function parse($url, $headonly = TRUE ){
    $agents = 'Mozilla/5.0 (X11; U; Linux i686; en-US) AppleWebKit/534.16 (KHTML, like Gecko) Chrome/10.0.648.204 Safari/534.16';
    try
    {
        $ch = curl_init();
        curl_setopt($ch, CURLOPT_HEADER, 0);
        curl_setopt($ch, CURLOPT_VERBOSE, FALSE);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);
        curl_setopt($ch, CURLOPT_FOLLOWLOCATION, TRUE);
        curl_setopt($ch, CURLOPT_USERAGENT, $agents);
        curl_setopt($ch, CURLOPT_URL, $url);
        $curlResp = curl_exec($ch);
        curl_close($ch);
        var_dump($curlResp); //RETURNS bool(false)
        die;

        $resp = str_replace("class=l","class='l'",$curlResp);
        return $resp;
    }
    catch( Exception $e)
    {
        $strResponse = "";
        $strErrorCode = $e->getCode();
        $strErrorMessage = $e->getMessage();
        print_r($arrCurlInfo, $strErrorCode, $strErrorMessage);
        die;
    }  //end catch
}
if ($curlResp === FALSE) {
    throw new Exception(); 
}

PHP Try Catch Example: Exception & Error Handling Tutorial

<?php
$denominator = 0;
echo 2 / $denominator;
?>
<?php
$denominator = 0;
if ($denominator != 0) {
    echo 2 / $denominator;
} else {
    echo "cannot divide by zero (0)";
}
?>
<?php
function my_error_handler($error_no, $error_msg)
{
    echo "Opps, something went wrong:";
    echo "Error number: [$error_no]";
    echo "Error Description: [$error_msg]";
}
set_error_handler("my_error_handler");
echo (5 / 0);
?>
<?php
error_reporting($reporting_level);
?>
<?php
echo $e->getMessage();
?>
<?php
echo $e->getCode();
?>
<?php
echo $e->getFile();
?>
<?php
echo $e->getLine();
?>
<?php
print_r( $e->getTrace());
?>
<?php
echo $e->getPrevious();
?>
<?php
echo $e->getTraceAsString();
?>
<?php
echo $e->__toString();
?>
<?php
throw new Exception("This is an exception example");
?>
<?php
try {
    //code goes here that could potentially throw an exception
}
catch (Exception $e) {
    //exception handling code goes here
}
?>
<?php
try {
    $var_msg = "This is an exception example";
    throw new Exception($var_msg);
}
catch (Exception $e) {
    echo "Message: " . $e->getMessage();
    echo "";
    echo "getCode(): " . $e->getCode();
    echo "";
    echo "__toString(): " . $e->__toString();
}
?>
<?php
class DivideByZeroException extends Exception {};
class DivideByNegativeException extends Exception {};
function process($denominator)
{
	try
	{
		if ($denominator == 0)
		{
			throw new DivideByZeroException();
		}
		else if ($denominator < 0)
		{
			throw new DivideByNegativeException();
		}
		else
		{
			echo 25 / $denominator;
		}
	}
	catch (DivideByZeroException $ex)
	{
		echo "DIVIDE BY ZERO EXCEPTION!";
	}
	catch (DivideByNegativeException $ex)
	{
		echo "DIVIDE BY NEGATIVE NUMBER EXCEPTION!";
	}
	catch (Exception $x)
	{
	echo "UNKNOWN EXCEPTION!";
	}
}
process(0);
?>

Next Lesson PHP Tutorial

Я использую функции PHP curl для отправки данных на веб-сервер с моей локальной машины. Мой код выглядит следующим образом:

$c = curl_init();

curl_setopt($c, CURLOPT_URL, $url);

curl_setopt($c, CURLOPT_RETURNTRANSFER, true);

curl_setopt($c, CURLOPT_POST, true);

curl_setopt($c, CURLOPT_POSTFIELDS, $data);

$result = curl_exec($c);

if (curl_exec($c) === false) {

    echo «ok»;

} else {

    echo «error»;

}

curl_close($c);

 К сожалению, я не могу поймать ни одной ошибки типа 404, 500 или сетевого уровня. Как же мне узнать, что данные не были размещены или получены с удаленного сервера?

Ответ 1

Вы можете использовать функцию curl_error(), чтобы определить, произошла ли какая-то ошибка. Например:

$ch = curl_init();

curl_setopt($ch, CURLOPT_URL, $your_url);

curl_setopt($ch, CURLOPT_FAILONERROR, true); // Требуется для того, чтобы коды ошибок HTTP сообщались через наш вызов к curl_error($ch)

//…

curl_exec($ch);

if (curl_errno($ch)) {

    $error_msg = curl_error($ch);

}

curl_close($ch);

if (isset($error_msg)) {

    // TODO — Обработать ошибку cURL соответствующим образом

}

Ответ 2

Если CURLOPT_FAILONERROR равно false, ошибки http не будут вызывать ошибок curl.

<?php

if (@$_GET[‘curl’]==»yes») {

  header(‘HTTP/1.1 503 Service Temporarily Unavailable’);

} else {

  $ch=curl_init($url = «http://».$_SERVER[‘SERVER_NAME’].$_SERVER[‘PHP_SELF’].»?curl=yes»);

  curl_setopt($ch, CURLOPT_FAILONERROR, true);

  $response=curl_exec($ch);

  $http_status = curl_getinfo($ch, CURLINFO_HTTP_CODE);

  $curl_errno= curl_errno($ch);

  if ($http_status==503)

    echo «HTTP Status == 503 <br/>»;

  echo «Curl Errno returned $curl_errno <br/>»;

}

Ответ 3

Вы можете сгенерировать ошибку curl после его выполнения:

$url = ‘http://example.com’;

$ch = curl_init($url);

curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

$result = curl_exec($ch);

if(curl_errno($ch)){

    echo ‘Request Error:’ . curl_error($ch);

}

 И вот коды ошибок curl:

если кому-то нужна дополнительная информация об ошибках curl

<?php

    $error_codes=array(

    [1] => ‘CURLE_UNSUPPORTED_PROTOCOL’,

    [2] => ‘CURLE_FAILED_INIT’,

    [3] => ‘CURLE_URL_MALFORMAT’,

    [4] => ‘CURLE_URL_MALFORMAT_USER’,

    [5] => ‘CURLE_COULDNT_RESOLVE_PROXY’,

    [6] => ‘CURLE_COULDNT_RESOLVE_HOST’,

    [7] => ‘CURLE_COULDNT_CONNECT’,

    [8] => ‘CURLE_FTP_WEIRD_SERVER_REPLY’,

    [9] => ‘CURLE_REMOTE_ACCESS_DENIED’,

    [11] => ‘CURLE_FTP_WEIRD_PASS_REPLY’,

    [13] => ‘CURLE_FTP_WEIRD_PASV_REPLY’,

    [14]=>’CURLE_FTP_WEIRD_227_FORMAT’,

    [15] => ‘CURLE_FTP_CANT_GET_HOST’,

    [17] => ‘CURLE_FTP_COULDNT_SET_TYPE’,

    [18] => ‘CURLE_PARTIAL_FILE’,

    [19] => ‘CURLE_FTP_COULDNT_RETR_FILE’,

    [21] => ‘CURLE_QUOTE_ERROR’,

    [22] => ‘CURLE_HTTP_RETURNED_ERROR’,

    [23] => ‘CURLE_WRITE_ERROR’,

    [25] => ‘CURLE_UPLOAD_FAILED’,

    [26] => ‘CURLE_READ_ERROR’,

    [27] => ‘CURLE_OUT_OF_MEMORY’,

    [28] => ‘CURLE_OPERATION_TIMEDOUT’,

    [30] => ‘CURLE_FTP_PORT_FAILED’,

    [31] => ‘CURLE_FTP_COULDNT_USE_REST’,

    [33] => ‘CURLE_RANGE_ERROR’,

    [34] => ‘CURLE_HTTP_POST_ERROR’,

    [35] => ‘CURLE_SSL_CONNECT_ERROR’,

    [36] => ‘CURLE_BAD_DOWNLOAD_RESUME’,

    [37] => ‘CURLE_FILE_COULDNT_READ_FILE’,

    [38] => ‘CURLE_LDAP_CANNOT_BIND’,

    [39] => ‘CURLE_LDAP_SEARCH_FAILED’,

    [41] => ‘CURLE_FUNCTION_NOT_FOUND’,

    [42] => ‘CURLE_ABORTED_BY_CALLBACK’,

    [43] => ‘CURLE_BAD_FUNCTION_ARGUMENT’,

    [45] => ‘CURLE_INTERFACE_FAILED’,

    [47] => ‘CURLE_TOO_MANY_REDIRECTS’,

    [48] => ‘CURLE_UNKNOWN_TELNET_OPTION’,

    [49] => ‘CURLE_TELNET_OPTION_SYNTAX’,

    [51] => ‘CURLE_PEER_FAILED_VERIFICATION’,

    [52] => ‘CURLE_GOT_NOTHING’,

    [53] => ‘CURLE_SSL_ENGINE_NOTFOUND’,

    [54] => ‘CURLE_SSL_ENGINE_SETFAILED’,

    [55] => ‘CURLE_SEND_ERROR’,

    [56] => ‘CURLE_RECV_ERROR’,

    [58] => ‘CURLE_SSL_CERTPROBLEM’,

    [59] => ‘CURLE_SSL_CIPHER’,

    [60] => ‘CURLE_SSL_CACERT’,

    [61] => ‘CURLE_BAD_CONTENT_ENCODING’,

    [62] => ‘CURLE_LDAP_INVALID_URL’,

    [63] => ‘CURLE_FILESIZE_EXCEEDED’,

    [64] => ‘CURLE_USE_SSL_FAILED’,

    [65] => ‘CURLE_SEND_FAIL_REWIND’,

    [66] => ‘CURLE_SSL_ENGINE_INITFAILED’,

    [67] => ‘CURLE_LOGIN_DENIED’,

    [68] => ‘CURLE_TFTP_NOTFOUND’,

    [69] => ‘CURLE_TFTP_PERM’,

    [70] => ‘CURLE_REMOTE_DISK_FULL’,

    [71] => ‘CURLE_TFTP_ILLEGAL’,

    [72] => ‘CURLE_TFTP_UNKNOWNID’,

    [73] => ‘CURLE_REMOTE_FILE_EXISTS’,

    [74] => ‘CURLE_TFTP_NOSUCHUSER’,

    [75] => ‘CURLE_CONV_FAILED’,

    [76] => ‘CURLE_CONV_REQD’,

    [77] => ‘CURLE_SSL_CACERT_BADFILE’,

    [78] => ‘CURLE_REMOTE_FILE_NOT_FOUND’,

    [79] => ‘CURLE_SSH’,

    [80] => ‘CURLE_SSL_SHUTDOWN_FAILED’,

    [81] => ‘CURLE_AGAIN’,

    [82] => ‘CURLE_SSL_CRL_BADFILE’,

    [83] => ‘CURLE_SSL_ISSUER_ERROR’,

    [84] => ‘CURLE_FTP_PRET_FAILED’,

    [84] => ‘CURLE_FTP_PRET_FAILED’,

    [85] => ‘CURLE_RTSP_CSEQ_ERROR’,

    [86] => ‘CURLE_RTSP_SESSION_ERROR’,

    [87] => ‘CURLE_FTP_BAD_FILE_LIST’,

    [88] => ‘CURLE_CHUNK_FAILED’);

    ?>

Ответ 4

Поскольку вы заинтересованы в отлове ошибок, связанных с сетью, и ошибок HTTP, ниже приведен лучший подход:

function curl_error_test($url) {

    $ch = curl_init();

    curl_setopt($ch, CURLOPT_URL, $url);

    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

    $responseBody = curl_exec($ch);

    /*

     * if curl_exec failed then

     * $responseBody равно false

     * curl_errno() возвращает ненулевое число

     * curl_error() возвращает непустую строку

     * Какой из них использовать — решать вам

     */

    if ($responseBody === false) {

        return «CURL Error: » . curl_error($ch);

    }

    $responseCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);

    /*

     * 4xx коды состояния — ошибки клиента

     * 5xx коды состояния — ошибки сервера

     */

    if ($responseCode >= 400) {

        return «HTTP Error: » . $responseCode;

    }

    return «Нет ошибки CURL или HTTP «;

}

 Тесты:

curl_error_test(«http://expamle.com»);          //  Ошибка CURL : Невозможно определить хост : expamle.com

curl_error_test(«http://example.com/whatever»); // Ошибка HTTP: 404

curl_error_test(«http://example.com»);          // Все в порядке с CURL или HTTP

Ответ 5

Еще один вариант кода:

  $responseInfo = curl_getinfo($ch);

    $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);

    $header_size = curl_getinfo($ch, CURLINFO_HEADER_SIZE);

    $body = substr($response, $header_size);

    $result=array();

    $result[‘httpCode’]=$httpCode;

    $result[‘body’]=json_decode($body);

    $result[‘responseInfo’]=$responseInfo;

    print_r($httpCode); 

     print_r($result[‘body’]); exit;

    curl_close($ch);

    if($httpCode == 403) {

        print_r(«Доступ запрещен»);

        exit;

    }   else {

         // другие ошибки 

     }

cURL — это инструмент, позволяющий взаимодействовать с различными серверами и поддерживающий множество протоколов: HTTP, FTP, TELNET и др. Изначально cURL — это служебная программа для командной строки. Но, к счастью для нас, PHP поддерживает работу с библиотекой cURL. В этой статье мы рассмотрим нетривиальные примеры работы с cURL.

Почему cURL?

На самом деле, есть много других способов отправить запрос на другой сервер чтобы, например, получить содержимое страницы. Многие, в основном из-за лени, используют простые PHP функции, вместо cURL:

$content = file_get_contents("http://www.example.com");

// или

$lines = file("http://www.example.com");

// или

readfile("http://www.example.com");

Однако они не позволяют эффективно обрабатывать ошибки. Также есть ряд задач, которые им вовсе не под силу — например, работа с cookies, авторизация, post запросы, загрузка файлов.

    cUrl — мощный инструмент, который поддерживает множество протоколов и предоставляет полную информацию о запросе.

Основы cUrl

Прежде чем перейти к сложным примерам, рассмотрим базовую структуру cURL запроса в PHP. Для выполнения cURL запроса в PHP необходимо сделать 4 основных шага:

  1. Инициализация.
  2. Установка опций.
  3. Выполнение запроса.
  4. Очистка ресурсов.
// 1. инициализация
$ch = curl_init();

// 2. устанавливаем опции, включая урл
curl_setopt($ch, CURLOPT_URL, "http://www.google.com");
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_HEADER, 0);

// 3. выполнение запроса и получение ответа
$output = curl_exec($ch);

// 4. очистка ресурсов
curl_close($ch);

В основном в этой статье мы будем рассматривать шаг №2, так как там происходит основная магия. Список cURL опций очень большой, поэтому все опции рассматривать сегодня мы не будем, а используем те, которые пригодятся для решения конкретных задач.

Отслеживание ошибок

При необходимости, вы можете добавить следующие строки для отслеживания ошибок:

// ...

$output = curl_exec($ch);

if ($output === FALSE) {

    echo "cURL Error: " . curl_error($ch);

}

// ...

Обратите внимание, мы используем «===» вместо «==», т.к. надо отличать пустой ответ сервера от булевского значения FALSE, которое возвращается в случае ошибки.

 Получение информации о запросе

Другой необязательный шаг — получение информации о cURL запросе, после его выполнения.

// ...

curl_exec($ch);

$info = curl_getinfo($ch);

echo 'Took ' . $info['total_time'] . ' seconds for url ' . $info['url'];

// ...

В результате вы получите массив со следующей информацией:

  • «url»
  • «content_type»
  • «http_code»
  • «header_size»
  • «request_size»
  • «filetime»
  • «ssl_verify_result»
  • «redirect_count»
  • «total_time»
  • «namelookup_time»
  • «connect_time»
  • «pretransfer_time»
  • «size_upload»
  • «size_download»
  • «speed_download»
  • «speed_upload»
  • «download_content_length»
  • «upload_content_length»
  • «starttransfer_time»
  • «redirect_time»

 Отслеживание редиректов, в зависимости от браузера

В этом примере мы напишем скрипт, который будет определять перенаправления в зависимости от разных настроек браузера. Например, некоторые сайты перенаправляют посетителей с мобильных устройств, посетителей из других стран.

Мы будем использовать опцию CURLOPT_HTTPHEADER для установки наших собственных заголовков, включая User-Agent и язык и посмотрим, куда перенаправляют нас сайты.

// URLs
$urls = array(
    "http://www.cnn.com",
    "http://www.mozilla.com",
    "http://www.facebook.com"
);
// браузеры
$browsers = array(

    "standard" => array (
        "user_agent" => "Mozilla/5.0 (Windows; U; Windows NT 6.1; en-US; rv:1.9.1.6) Gecko/20091201 Firefox/3.5.6 (.NET CLR 3.5.30729)",
        "language" => "en-us,en;q=0.5"
        ),

    "iphone" => array (
        "user_agent" => "Mozilla/5.0 (iPhone; U; CPU like Mac OS X; en) AppleWebKit/420+ (KHTML, like Gecko) Version/3.0 Mobile/1A537a Safari/419.3",
        "language" => "en"
        ),

    "french" => array (
        "user_agent" => "Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 5.1; GTB6; .NET CLR 2.0.50727)",
        "language" => "fr,fr-FR;q=0.5"
        )

);

foreach ($urls as $url) {

    echo "URL: $urln";

    foreach ($browsers as $test_name => $browser) {

        $ch = curl_init();

        // установим адрес
        curl_setopt($ch, CURLOPT_URL, $url);

        // укажем используемый браузер и язык
        curl_setopt($ch, CURLOPT_HTTPHEADER, array(
                "User-Agent: {$browser['user_agent']}",
                "Accept-Language: {$browser['language']}"
            ));

        // содержимое страницы нам не нужно
        curl_setopt($ch, CURLOPT_NOBODY, 1);

        // нужны только заголовки
        curl_setopt($ch, CURLOPT_HEADER, 1);

        // вернем результат, вместо его вывода
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);

        $output = curl_exec($ch);

        curl_close($ch);

        // определим перенаправления в HTTP заголовках?
        if (preg_match("!Location: (.*)!", $output, $matches)) {

            echo "$test_name: redirects to $matches[1]n";

        } else {

            echo "$test_name: no redirectionn";

        }

    }
    echo "nn";
}

В цикле проверяем браузеры для каждого урла. Сперва мы устанавливаем опции для нашего запроса: URL и тестируемый браузер и язык.

Т.к. мы установили специальную опцию, результат выполнения запроса будет содержать только HTTP заголовки. С помощью простого регулярного выражения мы можем проверить содержит ли ответ строку «Location:».

Результат выполнения скрипта:

URL: http://www.cnn.com
standard: redirects to http://edition.cnn.com/
iphone: redirects to http://edition.cnn.com/
french: redirects to http://edition.cnn.com/

URL: http://www.mozilla.com
standard: redirects to https://www.mozilla.org/firefox/
iphone: redirects to https://www.mozilla.org/firefox/
french: redirects to https://www.mozilla.org/firefox/

URL: http://www.facebook.com
standard: redirects to https://www.facebook.com/
iphone: redirects to http://m.facebook.com/?refsrc=http%3A%2F%2Fwww.facebook.com%2F&_rdr
french: no redirection

Отправляем POST запросы

При выполнении GET запросов данные можно передавать в строке запроса. Например, когда вы ищете в гугле, ваш запрос передается в URL:

http://www.google.com/search?q=google

Чтобы получить результат этого запроса, вам даже не понадобится cURL, вы можете быть ленивым и использовать «file_get_contents()».

Но некоторые HTML формы используют метод POST. В таком случае данные отправляются в теле сообщения запроса, а не в самом URL.

Напишем скрипт, который будет отправлять POST запросы. Для начала создадим простой PHP файл, который будет принимать эти запросы и возвращать отправленные ему данные. Назовем его post_output.php:

print_r($_POST);

Далее напишем PHP скрипт, который отправит cURL запрос:

$url = "http://localhost/post_output.php";

$post_data = array (
    "foo" => "bar",
    "query" => "FooBar",
    "action" => "Submit"
);

$ch = curl_init();

curl_setopt($ch, CURLOPT_URL, $url);

curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
// делаем POST запрос
curl_setopt($ch, CURLOPT_POST, 1);
// добавляем данные
curl_setopt($ch, CURLOPT_POSTFIELDS, $post_data);

$output = curl_exec($ch);

curl_close($ch);

echo $output;

Данный скрипт выведет:

Array
(
    [foo] => bar
    [query] => FooBar
    [action] => Submit
)

Данный скрипт отправил POST запрос файлу post_output.php. который вывел содержимое массива $_POST и мы получили этот ответ с помощью cURL.

Загрузка файлов

Загрузка файлов очень похожа на предыдущий скрипт, т.к. загрузка файлов всегда выполняется с помощью POST запросов.

Так же как и в предыдущем примере, создадим файл, который будет принимать запросы, upload_output.php:

print_r($_FILES);

И сам скрипт, загружающий файлы:

$url = "http://localhost/upload_output.php";

$post_data = array (
    "foo" => "bar",
    // файл для загрузки
    "upload" => "@/tmp/desert.jpg"
);

$ch = curl_init();

curl_setopt($ch, CURLOPT_URL, $url);

curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);

curl_setopt($ch, CURLOPT_POST, 1);

curl_setopt($ch, CURLOPT_POSTFIELDS, $post_data);

$output = curl_exec($ch);

curl_close($ch);

echo $output;

Если вы хотите загрузить файл, все что необходимо — это передать путь к нему, так же как обычный параметр POST запроса, поставив вначале «@». Результат работы скрипта:

Array
(
    [upload] => Array
        (
            [name] => desert.jpg
            [type] => application/octet-stream
            [tmp_name] => /tmp/phpAhEvXy
            [error] => 0
            [size] => 845941
        )

)

Multi cURL

Одна из продвинутых возможностей cURL в PHP — это возможность выполнения нескольких запросов одновременно и асинхронно.

В обычных условиях скрипт останавливается и ждет выполнения запроса. И если вам надо выполнить много запросов, то это может занять много времени, т.к. вы будете выполнять последовательно. Это ограничение можно обойти:

// создаем обработчики
$ch1 = curl_init();
$ch2 = curl_init();

// устанавливаем опции
curl_setopt($ch1, CURLOPT_URL, "http://lxr.php.net/");
curl_setopt($ch1, CURLOPT_HEADER, 0);
curl_setopt($ch2, CURLOPT_URL, "http://www.php.net/");
curl_setopt($ch2, CURLOPT_HEADER, 0);

//create the multiple cURL handle
$mh = curl_multi_init();

// добавляем обработчики
curl_multi_add_handle($mh,$ch1);
curl_multi_add_handle($mh,$ch2);

$running = null;
// выполняем запросы
do {
    curl_multi_exec($mh, $running);
} while ($running > 0);

// освободим ресурсы
curl_multi_remove_handle($mh, $ch1);
curl_multi_remove_handle($mh, $ch2);
curl_multi_close($mh);

Идея состоит в том, что вы можете создать множество cURL дескрипторов, объединить их под одним мульти-дескриптором и выполнять их асинхронно.

Сначала все как и с обычным cURL запросом — создается дескриптор (curl_init()), задаются параметры (curl_setopt()). Далее создается мульти-дескриптор (curl_multi_init()) и добавляются ранее созданные обычные дескрипторы (curl_multi_add_handle()). Вместо обычного вызова curl_exec() мы будем многократно вызывать curl_multi_exec() данная функция информирует нас о количестве активных соединений с помощью второго параметра — $running. Поэтому цикл работает пока $running не станет равным 0. И, конечно, после окончания работы необходимо освободить ресурсы.

В данном примере мы просто выводим результат запросов в STDOUT. Рассмотрим нетривиальный случай применения multi cURL.

Проверка внешних ссылок в WordPress

Представьте себе блог с большим количеством постов, содержащих ссылки на внешние сайты. Некоторые из этих ссылок могут быть не рабочими.

Напишем скрипт, который найдет все нерабочие ссылки и покажет их нам.

Для начала нам необходимо вытащить все внешние ссылки из базы данных:

// CONFIG
$db_host = 'localhost';
$db_user = 'root';
$db_pass = '';
$db_name = 'wordpress';
$excluded_domains = array('localhost', 'easy-code.ru');
$max_connections = 10;

$url_list = array();
$working_urls = array();
$dead_urls = array();
$not_found_urls = array();
$active = null;

// соединимся с MySQL
if (!mysql_connect($db_host, $db_user, $db_pass)) {
    die('Could not connect: ' . mysql_error());
}

if (!mysql_select_db($db_name)) {
    die('Could not select db: ' . mysql_error());
}

// берем все посты со ссылками в тексте
$q = "SELECT post_content FROM wp_posts
    WHERE post_content LIKE '%href=%'
    AND post_status = 'publish'
    AND post_type = 'post'";
$r = mysql_query($q) or die(mysql_error());

while ($d = mysql_fetch_assoc($r)) {
    // собираем все ссылки с помощью регулярки
    if (preg_match_all("/href="(.*?)"/", $d['post_content'], $matches)) {
        foreach ($matches[1] as $url) {
            // фильтруем ненужные домены
            $tmp = parse_url($url);

            if (isset($tmp['host']) && in_array($tmp['host'], $excluded_domains)) {
                continue;
            }

            // собираем вместе
            $url_list [] = $url;
        }
    }
}

// удаляем повторения
$url_list = array_values(array_unique($url_list));

if (!$url_list) {
    die('No URL to check');
}

В этой части скрипта мы просто вытаскиваем из базы все внешние ссылки. Проверим их:

$mh = curl_multi_init();

// 1. добавим ссылки
for ($i = 0; $i < $max_connections; $i++) {
    add_url_to_multi_handle($mh, $url_list);
}

// основной цикл
do {
    curl_multi_exec($mh, $curRunning);

    // 2. один из потоков завершил работу
    if ($curRunning != $running) {
        $mhinfo = curl_multi_info_read($mh);

        if (is_array($mhinfo) && ($ch = $mhinfo['handle'])) {
            // 3. один из запросов выполнен, можно получить информацию о нем
            $info = curl_getinfo($ch);

            // 4. нерабочая ссылка
            if (!$info['http_code']) {
                $dead_urls[] = $info['url'];

            // 5. 404?
            } else if ($info['http_code'] == 404) {
                $not_found_urls[] = $info['url'];

            // 6. верная ссылка
            } else {
                $working_urls[] = $info['url'];
            }

            // 7. удаляем отработавший дескриптор
            curl_multi_remove_handle($mh, $mhinfo['handle']);
            curl_close($mhinfo['handle']);

            // 8. добавим новый урл
            add_url_to_multi_handle($mh, $url_list);
            $running = $curRunning;
        }
    }
} while ($curRunning > 0);

curl_multi_close($mh);

echo "==Dead URLs==n";
echo implode("n", $dead_urls) . "nn";

echo "==404 URLs==n";
echo implode("n", $not_found_urls) . "nn";

echo "==Working URLs==n";
echo implode("n", $working_urls);
echo "nn";

// 9. добавляет дескриптор с заданным урлом
function add_url_to_multi_handle($mh, $url_list) {
    static $index = 0;

    // если еще есть ссылки
    if (isset($url_list[$index])) {
        // все как обычно
        $ch = curl_init();

        // устанавливаем опции
        curl_setopt($ch, CURLOPT_URL, $url_list[$index]);
        // возвращаем, а не выводим результат
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        // разрешаем редиректы
        curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
        // получаем только заголовки для экономии времени
        curl_setopt($ch, CURLOPT_NOBODY, 1);

        // добавляем к мульти-дескриптору
        curl_multi_add_handle($mh, $ch);

        $index++;
    }
}

Рассмотрим код подробнее (нумерация соответствует комментариям в коде):

  1. Добавляем начальное количество дескрипторов, чтобы не перегружать систему потоками. Количество регулируется переменной $max_connections.
  2. В переменной $curRunning хранится количество работающих потоков, в $running — предыдущее значение, если они станут не равными, то один из потоков завершил работу.
  3. Получаем информацию о выполненном запросе.
  4. Если нет ответа сервера — ссылка не рабочая.
  5. Ответ сервера — 404.
  6. Иначе ссылка работает.
  7. Запрос выполнен, освобождаем ресурсы.
  8. Добавим новый урл к мульти дескриптору.
  9. Функция add_url_to_multi_handle() добавляет новый дескриптор с заданным урлом к мульти-дескриптору.

Запустим скрипт:

==Dead URLs==
xample1234.com/

==404 URLs==
www.google.com/dsfasdfafd

==Working URLs==
ru.php.net/manual/ru/function.time.php
www.cssbuttongenerator.com/
csslint.net/
codex.wordpress.org/Plugin_API/Action_Reference
fortawesome.github.io/Font-Awesome/
fortawesome.github.io/Font-Awesome/
www.oracle.com/technetwork/java/javafx/downloads/index.html
codex.wordpress.org/Plugin_API/Filter_Reference
codex.wordpress.org/Roles_and_Capabilities
code.google.com/p/google-api-php-client/wiki/OAuth2#Google_APIs_Console
jplayer.org/
code.google.com/p/google-api-php-client/
developers.google.com/+/
accounts.google.com/ServiceLogin?service=devconsole&passive=1209600&continue=https%3A%2F%2Fcode.google.com%2Fapis%2Fconsole%2F&followup=https%3A%2F%2Fcode.google.com%2Fapis%2Fconsole%2F
daneden.github.io/animate.css/
github.com/daneden/animate.css
ru2.php.net/manual/ru/function.autoload.php
www.google.com/recaptcha/api/verify
phpunit.de/
phpunit.de/manual/current/en/phpunit-book.html

Проверка заняла около 2 секунд. Запуская одновременно по 10 потоков производительность возрастает в 10 раз, по сравнению с обычными cURL запросами. Чтобы получить содержимое ответа сервера используйте функцию curl_multi_getcontent($ch), где $ch — дескриптор, полученный из curl_multi_info_read().

Другие возможности cURL в PHP

HTTP аутентификация

Если HTTP запрос требует аутентификацию, используйте следующий код:

$url = "http://www.somesite.com/members/";

$ch = curl_init();

curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);

// отправляем имя и пароль
curl_setopt($ch, CURLOPT_USERPWD, "myusername:mypassword");

// если разрешить редиректы
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
// cURL отправит пароль и после перенапрвлений
curl_setopt($ch, CURLOPT_UNRESTRICTED_AUTH, 1);

$output = curl_exec($ch);

curl_close($ch);

Загрузка по FTP

В PHP есть своя библиотека для работы с FTP, но можно использовать и cURL:

// читаем файл
$file = fopen("/path/to/file", "r");

// урл уже содержит необходимые данные
$url = "ftp://username:password@mydomain.com:21/path/to/new/file";

$ch = curl_init();

curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);

// опции
curl_setopt($ch, CURLOPT_UPLOAD, 1);
curl_setopt($ch, CURLOPT_INFILE, $fp);
curl_setopt($ch, CURLOPT_INFILESIZE, filesize("/path/to/file"));
curl_setopt($ch, CURLOPT_FTPASCII, 1);

$output = curl_exec($ch);
curl_close($ch);

Использование прокси

Запросы можно выполнять через определенный proxy:

$ch = curl_init();

curl_setopt($ch, CURLOPT_URL,'http://www.example.com');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);

// адрес прокси
curl_setopt($ch, CURLOPT_PROXY, '11.11.11.11:8080');

// если требуется авторизация
curl_setopt($ch, CURLOPT_PROXYUSERPWD,'user:pass');

$output = curl_exec($ch);

curl_close ($ch);

Колбэки (callback functions)

Есть возможность использовать колбэки во время выполнения запроса, не дожидаясь его завершения. Например, во время того как ответ сервера загружается мы можем использовать уже полученные данные, не дожидаясь полной загрузки.

$ch = curl_init();

curl_setopt($ch, CURLOPT_URL,'http://example.com');
curl_setopt($ch, CURLOPT_WRITEFUNCTION,"progress_function");

curl_exec($ch);

curl_close ($ch);

function progress_function($ch,$str) {
    echo $str;
    return strlen($str);
}

Колбэк функция должна возвращать длину строки для правильной работы запроса.

Каждый раз, когда будет получена очередная часть ответа сервера, будет вызван колбэк.

Заключение

В этой статье мы рассмотрели продвинутые возможности cURL в PHP. В следующий раз, когда вам понадобится делать URL запросы — используйте cURL.

На этом всё!

Понравилась статья? Поделить с друзьями:

Читайте также:

  • Curl error code 1020
  • Curl error 77 error setting certificate verify locations
  • Curl error 7 failed to connect to downloads wordpress org port 443 connection refused
  • Curl error 7 couldn t connect to server
  • Curl error 60 while downloading composer

  • 0 0 голоса
    Рейтинг статьи
    Подписаться
    Уведомить о
    guest

    0 комментариев
    Старые
    Новые Популярные
    Межтекстовые Отзывы
    Посмотреть все комментарии