Skip to content

Partially support first-class callable syntax in constant expressions #9236

Closed as not planned

Description

@pevdh

Description

The first-class callable syntax is currently not allowed in constant expressions:

class X {
    const FN = strlen(...);
}

var_dump((X::FN)('test'));
// PHP Fatal error:  Constant expression contains invalid operations

I propose partially supporting the first-class callable syntax in a constant expression. Specifically, I propose that PHP allows these two cases in a constant context:

class X {
    const A = strlen(...);
    const B = SomeClass::someStaticMethod(...);
}

While (still) disallowing expressions that cannot be known at compile time:

class X {
    const C = $closure(...);
    const D = $obj->method(...);
    const E = ($obj->property)(...);
    // etc. See the first-class callables RFC for a complete list
}

Example

Symfony's Choice assertion allows the user to specify a callback. It would be nice if we could use the first-class callable syntax in attributes, but this is currently not allowed:

use Symfony\Component\Validator\Constraints as Assert;

class User {
     #[Assert\Choice(callback: Role::values(...))] // Using this syntax here causes an error
     public string $role;
}

enum Role: string
{
    case Customer = 'customer';
    case Admin = 'admin';
    
    public static function values() {
        return array_map(fn (Role $a) => $a->name, self::cases());
    }
}

Implementation

I hacked together a working patch that supports the strlen(...) syntax in constant expressions. I haven't gotten around to implementing SomeClass::someStaticFunction(...) yet. There are probably some edge cases that I'm missing - I'm not too familiar with the PHP code base.

I'm also not sure if this feature would require an RFC. I would imagine it would, though.

Please let me know what you think.

Activity

  1. cmb69 commented on Aug 3, 2022

    @cmb69
    Member

    Yeah, I think there should be an RFC to discuss and clarify the details. Note that there is also #8959 which is a more general feature request.

  2. github-actions commented on Nov 2, 2022

    @github-actions

    There has not been any recent activity in this feature request. It will automatically be closed in 14 days if no further action is taken. Please see https://github.com/probot/stale#is-closing-stale-issues-really-a-good-idea to understand why we auto-close stale feature requests.

  3. gnumoksha commented on Nov 9, 2022

    @gnumoksha

    Please, Mr Bot, don't close this :)

  4. cmb69 commented on Nov 9, 2022

    @cmb69
    Member

    See https://wiki.php.net/rfc/howto, if you're interested in pursuing this.

  5. mvorisek commented on Nov 10, 2022

    @mvorisek
    Contributor

    I expect this to be fixed by #9301 no RFC proposed yet

  6. bwoebi commented on Nov 10, 2022

    @bwoebi
    Member

    @mvorisek Not sure what you are referring to. That PR is about static variables in functions, not constant expressions in general.

  7. github-actions commented on Feb 9, 2023

    @github-actions

    There has not been any recent activity in this feature request. It will automatically be closed in 14 days if no further action is taken. Please see https://github.com/probot/stale#is-closing-stale-issues-really-a-good-idea to understand why we auto-close stale feature requests.

  8. mvorisek commented on Mar 11, 2023

    @mvorisek
    Contributor

    Any CTE expression like strlen - https://3v4l.org/08SOl - should be supported in constant expression.

  9. KapitanOczywisty commented on Mar 11, 2023

    @KapitanOczywisty

    If function would be mistakenly added to CTE, but would be causing errors, you can just remove it in the next patch version and no one will notice. Removing function from constant expression would cause breaks. Then as an user, how do you even keep track which function are available for constant expressions? I could also imagine that this would require significant rework to implement.

  10. github-actions commented on Jun 10, 2023

    @github-actions

    There has not been any recent activity in this feature request. It will automatically be closed in 14 days if no further action is taken. Please see https://github.com/probot/stale#is-closing-stale-issues-really-a-good-idea to understand why we auto-close stale feature requests.

  11. dynasource commented on Feb 21, 2024

    @dynasource

    +1

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions