php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #81036 TypeError is raised instead of implizit type casting
Submitted: 2021-05-12 10:23 UTC Modified: 2021-05-17 14:12 UTC
From: bugs-php at daniel-siepmann dot de Assigned:
Status: Not a bug Package: *Programming Data Structures
PHP Version: 7.4.19 OS: Ubuntu
Private report: No CVE-ID: None
 [2021-05-12 10:23 UTC] bugs-php at daniel-siepmann dot de
Description:
------------
Given a script without declare_strict but a method with defined return type.
The method returns an integer but the stored value might be a string.

I would expect PHP to do a type cast which works in general.
But it does not work with example string.

Test script:
---------------
class Test
{
    protected $property;
    public function __construct() {
        $this->property = 10;
    }
    public function getProperty(): ?int {
        return $this->property;
    }
    public function setProperty($value) {
        $this->property = $value;
    }
}
$subject = new Test;
var_dump($subject->getProperty()); // works
$subject->setProperty((int) '{$PID.event.import.ismf.storagePid}'); // works
var_dump($subject->getProperty()); // works
$subject->setProperty('{$PID.event.import.ismf.storagePid}'); // works
var_dump($subject->getProperty()); // breaks



Expected result:
----------------
I would expect the last line to return the integer 0 instead of an TypeError.

Actual result:
--------------
The script fails with

PHP Fatal error:  Uncaught TypeError: Return value of Test::getProperty() must be of the type int, string returned

Patches

Pull Requests

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2021-05-12 10:27 UTC] nikic@php.net
-Status: Open +Status: Not a bug
 [2021-05-12 10:27 UTC] nikic@php.net
Explicit type casts like (int) perform a cast at all costs, even if it makes absolutely no sense -- you can cast "foobar" to int, you can cast [1, 2, 3] to int, you can cast new stdClass to int.

Type declarations have much stricter rules, even if strict_types is not used. They only allow conversions if they are "somewhat reasonable". In particular, you can implicitly convert "10" to 10, but you can't implicitly convert "foobar" to 0. If you want to do that, you need to use an explicit type cast.

This is by design.
 [2021-05-12 11:06 UTC] bugs-php at daniel-siepmann dot de
Thanks for the near instant response.

I fully understand that design. Still I'm lacking a proper info within docs. I would like to figure out how to contribute there.

I guess the design is already documented via "if possible" at https://www.php.net/manual/en/language.types.declarations.php#language.types.declarations.strict ?
I would then try to improve that part.
 [2021-05-17 14:12 UTC] girgias@php.net
The best way to contribute is to fork the git repo on GitHub (https://github.com/php/doc-en/) and submit a PR.

In this instance it might make sense to rework the type-juggling page (https://github.com/php/doc-en/blob/master/language/types/type-juggling.xml) to include information about it with respect to type declarations.
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Thu Oct 03 18:01:27 2024 UTC