On 10 Nov 2023, at 11:11, Kamil Tekiela <tekiela...@gmail.com> wrote:
>> That's what I thought, but for some reason, casting null is deprecated only 
>> when it's provided as an argument to functions, all other cases it's fine... 
>> weird right?
> 
> 
> No, passing null to non-nullable parameters is already an error. It has been 
> for a long while now. The only exception are some built-in functions that 
> silently ignored that and cast the value to another type. 

Not sure I'm following, I said "an argument to functions", the other cases I 
was referring to was string concatenation, == comparisons, arithmetics, 
sprintf, print, echo, array keys, etc.



> However, passing null to non-nullable param was never allowed. 

For user defined functions... but there are at least 335 parameters negatively 
affected by this deprecation:

https://github.com/craigfrancis/php-allow-null-rfc/blob/main/functions-change.md

And that's ignoring the 104 questionable and 558 problematic parameters where 
NULL (or empty string) probably shouldn't be allowed (like how $separator in 
explode() already has a “cannot be empty” Fatal Error).



> but as I explained earlier it was always an error. That's how the language 
> was designed.

I'm not sure many people see it like that though, most of the frameworks can 
return NULL when retrieving GET/POST/DB etc values, and developers simply pass 
those nullable values to functions like trim(), urlencode(), hash(), 
base64_encode(), strtoupper(), preg_match(), etc.



> Finding it is difficult, I agree, but that's the whole purpose of the 
> deprecation. It's supposed to help you find all the mistakes. The mistakes 
> are only with built-in functions, so the scope is very limited.

Imagine a developer creating a simple search <form>, so the browser makes a 
request to "/search/?q=x", and the developer works with the q value, maybe they 
use `htmlspecialchars`, or `preg_split` to separate the words, etc... during 
all of their (probably manual) testing, they are always providing a value, as 
they are using the website as they expect it to be used, but a few months 
later, when it's in production, a user types in the "/search/" URL, or edits 
the URL, or the page with the form on failed to load properly, or a browser 
extension did something to it; today the script would receive a NULL value, and 
it would be treated like an empty string (as expected and documented), but with 
PHP 9, this will cause a fatal error?



> Casting null to other types is not a mistake, but passing null to functions 
> that don't expect it, is a mistake.

But that's what the type coercion is supposed to do, like how a function that 
expects an integer will accept the string '5'.



> Just think about a simple example and how ambiguous it would be. 
> 
> function abc(string|int $p) {}
> abc(null); 
> 
> What should null be converted into and why?

int(0), because union types already define an "order of preference":

https://wiki.php.net/rfc/union_types_v2#coercive_typing_mode

Like this:

```
function abc(string|int $p) {
  var_dump($p); // int(0)
}

abc(false);
```

Craig

Reply via email to