I am updating my project from PHP 7.0 to PHP 8.0 and I couldn't find out, if it is allowed to EXPLICITLY assign resource as the data type:
- of a class property,
- of a method/function parameter,
- returned by a method/function,
What I know right now is, that:
resourceis one of the types building the mixed type,- some internal functions, like fopen, are returning the type
resource.
Until now I read:
- all official manuals regarding migrating to PHP 8: PHP: Migrating from PHP 5.5.x to PHP 5.6.x, ..., PHP: Migrating from PHP 7.4.x to PHP 8.0.x;
- The whole content on PHP.Watch: PHP Versions;
- The whole content on Lindevs: PHP.
Am I missing something, somewhere?
Thank you for your time.
For more clarity, this is how I want to use the resource data type in my project (PSR-7 implementation):
<?php
namespace MyPackages\Http\Message;
use Psr\Http\Message\StreamInterface;
/**
* Stream.
*/
class Stream implements StreamInterface {
/**
* A stream, e.g. a resource of type "stream".
*
* @var resource
*/
private resource $stream;
/**
* @param string|resource $stream A filename, or an opened resource of type "stream".
* @param string $accessMode (optional) Access mode. 'r': Open for reading only.
*/
public function __construct(string|resource $stream, string $accessMode = 'r') {
$this->stream = $this->buildStream($stream, $accessMode);
}
/**
* Build a stream from a filename or an opened resource of type "stream".
*
* Not part of PSR-7.
*
* @param string|resource $stream Filename, or resource.
* @param string $accessMode Access mode.
* @return resource
* @throws \RuntimeException If the file cannot be opened.
* @throws \InvalidArgumentException If the stream or the access mode is invalid.
*/
private function buildStream(string|resource $stream, string $accessMode): resource {
if (is_string($stream)) {
//... some validations ...
/*
* Open the file specified by the given filename.
* E.g. create a stream from the filename.
* E.g. create a resource of type "stream" from the filename.
*/
try {
$stream = fopen($stream, $accessMode);
} catch (\Exception $exception) {
throw new \RuntimeException('The file "' . $stream . '" could not be opened.');
}
} elseif (is_resource($stream)) {
if ('stream' !== get_resource_type($stream)) {
throw new \InvalidArgumentException('The provided resource must be an opened resource of type "stream".');
}
}
return $stream;
}
}
No, you cannot type hint with
resource.Here's an RFC from 2015 where it was brought up, here's the PR with the implementation, and here's a thread of discussion on it.
The gist is that the PHP community wants to get rid of resources because they represent an older way of doing things. Also,
resourceis too generic, basically equivalent toobjectthat it doesn't provide much, if any benefit.From the discussion:
And