PHP 8.0 : CurlHandle object in curl_* functions
27, June 2020

PHP internals are trying to slowly replace all usage of 'resource' in PHP with appropriate Object for a long time. Resources are mess in PHP. They are not actually any data type at all. Using Object instead of resource is much better approach and PHP internals are trying to achieve that.

In PHP 8.0, all curl_* functions will work with CurlHandle object instance, previousely curl_* used resource instead.


So, How do curl_* functions work now?

Previously, curl_init() used to return resource or false:

<?php
$ch = curl_init();

var_dump($ch);
//  resource(1) of type (curl)

But now it returns CurlHandle Object or false:

<?php
$ch = curl_init();

var_dump($ch);
// object(CurlHandle)#1 (0) {}

Note: curl_multi_init() now returns CurlMultiHandle object. Similarly curl_share_init() now returns CurlShareHandle object.


After init, every other function works like before, they just accept an object as handler now:

$ch = curl_init();
// $ch is now a object of CurlHandle

curl_setopt($ch, CURLOPT_URL, "example.com");
// curl_setopt accepts CurlHandle object instance as first parameter

curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);

// same, curl_exec now accepts CurlHandle object instance
$output = curl_exec($ch);

As we see, we don't need to change our code for this new change.

So, Our previous code will run fine?

It should. But be carefull if you are using is_resource() to verify curl_init() return. As curl_init() does not return resource anymore, is_resource() will not work on it. If you want to check if curl_init() return value is valid, check if it is false, because curl_init returns false on failure.

$handle = curl_init();

if (!\is_resource($handle)) {
  // this will not work anymore 
  //don't do this 
}

if ($handle === false) {
 // if $handle is false that means curl_init failed
 throw_or_log_this_error()
}

// $handle is valid here

How will we close curl or free the resource?

curl_close() does not close the resource any more. duh, there is no resource to close. As curl_* now works with object, and just like any other object, PHP close/frees them when there are no reference left to them or at end of the script execution.

So, generally you are not required to call curl_close() anymore.

But, I want to close curl manually

If you want to close curl manually for some reason, you can simply unset them.

$curl = curl_init();
// we will use it here
curl_close($curl); // not needed anymore
unset($curl); // CurlHandle object destroyed


Reference: https://github.com/php/php-src/pull/5402