Search code examples
phpclassstandardstraits

Can I call a static function from a trait outside of a class?


Consider the situation where there are multiple classes that all need to have access to the configuration storage mechanism, but cannot be extended from a base class because of the architectuur of the framework. In addition to that I wanted to keep the storage mechanism flexible (be able to switch storage backend later).

I felt it would make sense to create a trait which does the actual saving and use those functions inside all classes (for the example I use $_SESSION as storage system):

trait MyTrait {

  function setting_enabled() {
    return !empty($_SESSION['setting']) ? TRUE : FALSE;
  }

  function enable_setting() {
    $_SESSION['setting'] = TRUE;
  }

  function disable_setting() {
    $_SESSION['setting'] = FALSE;
  }

}

This works great from classes. There is however also one file that is not a class, but is just plain PHP, for which I also need to know if the setting is enabled.

I have tried declaring the function as static:

trait MyTrait {

  static function setting_enabled() { // Declared as static function
    return !empty($_SESSION['setting']) ? TRUE : FALSE;
  }

  ...
}

And then call the static function from the trait, which worked fine.

if (MyTrait::setting_enabled()) {
  ...
}

It however feels not entirely right. On the other hand, creating a new empty class that uses the trait and instantiating that to obtain the value seems like a lot of overhead.

Am I allowed to do this (as of PHP 5.6, but also considering the future with PHP 7.x)?


Solution

  • PHP does not allow calling trait's methods without some class (no matter if static or not).

    A simple workaround is to use an anonymous class mediately:

    
    ...
    
    (new class { use MyTrait; })::myMethod();
    
    ...
    
    

    I like this way a little bit more because we don't create an unnecessary class name.