On Fri, Jul 26, 2024, at 23:54, Bilge wrote: > Hi Internals, > > New RFC idea just dropped. When writing a function, we can specify defaults > for its parameters, and when calling a function we can leverage those > defaults *implicitly* by not specifying those arguments or by "jumping over" > some of them using named parameters. However, we cannot *explicitly* use the > defaults. But why would we want to? > > Sometimes we want to effectively *inherit* the defaults of a function we're > essentially just proxying. One way to do that is copy and paste the entire > method signature, but if the defaults of the proxied method change, we're now > overriding them with our own, which is not what we wanted to do. It is > possible, in a roundabout way, to avoid specifying the optional parameters by > filtering them out (as shown in the next example). The final possibility is > to use reflection and literally query the default value for each optional > parameter, which is the most awkward and verbose way to inherit defaults. > > Let's use a concrete example for clarity. > > function query(string $sql, int $limit = PHP_INT_MAX, int $offset = 0); > > > > function myQuery(string $sql, ?int $limit = null, ?int $offset = null) { > query(...array_filter(func_get_args(), fn ($arg) => $arg !== null)); > } > > > In this way we are able to filter out the null arguments to inherit the > callee defaults, but this code is quite ugly. Moreover, it makes the > (sometimes invalid) assumption that we're able to use `null` for all the > optional arguments. > > In my new proposal for *explicit *callee defaults, it would be possible to > use the `default` keyword to expressly use the default value of the callee in > that argument position. For example, the above implementation for myQuery() > could be simplified to the following. > > > > function myQuery(string $sql, ?int $limit = null, ?int $offset = null) { > query($sql, $limit ?? default, $offset ?? default); > } > > > Furthermore, it would also be possible to "jump over" optional parameters > *without* using named parameters. > > json_decode($json, true, default, JSON_THROW_ON_ERROR); > > This proposal is built on the assumption that it is possible to specify that > PHP should only accept the `default` expression in method and function call > contexts. For example, it would not be valid to return `default` from a > function and substitute it that way; my proposal is to only permit `default` > in literal function calling contexts. My knowledge of internals is > insufficient (read: non-existent) to know whether or not this restriction is > possible to implement, but if it is, I think this is a good idea. What do you > think? > > > > Cheers, > Bilge > >
This seems like a case for code generation — and an RFC that provides hooks for code generation would probably be better IMHO. There are a couple of neat tools out there doing this and hooking into composer, like https://packagist.org/packages/olvlvl/composer-attribute-collector There are many things that could benefit from this, such as DI containers, scanning for attributes, generating efficient serializers/deserializers, etc. — Rob