Hi there,
I've been reading with interest about the new FFI class that has been
introduced in PHP 7.4 [1].
However, I was surprised to see that the class includes bivalent methods,
that is to say methods that can be called both statically and
non-statically. For example, new() [2], which can be called as:
FFI::new(...)
or non-statically:
$objFFI->new(...)
(Note that the latter is not simply a short-cut to the former, as it
accesses the instance properties.)
As you can see, this is a very useful design pattern, but it is one that is
currently disallowed in userland code:
-
If you declare a method as static, you can call it in both ways, but in
neither case can you access the instance properties or any other instance
functionality ($this is undefined). -
If you don't declare the method as static, and call it statically, you get
a deprecation notice:Deprecated: Non-static method MyClass::MyMethod() should not be called
statically in file.php on line X
This FFI class is therefore introducing an inconsistency in the language.
My understanding is that the general direction of travel is to try and
remove language inconsistencies, where possible, so introducing new ones
seems like something that should be strongly avoided where possible.
My preference would be to resolve this inconsistency by un-deprecating the
uses of non-static methods in a static context. As per the example in the
FFI class, there are clearly use-cases where both methods of calling a
function are desirable. We have a number of such examples in our code (e.g.
we have a GetMonthName() function in our date class, which can either
operate on an instantiated object or be called statically with any date-like
argument). These functions currently detect the context and only access
$this when called non-statically. Correctly implemented, this type of
overloading leads to very clean interfaces (though I understand the risks
that inexperienced programmers might face).
Alternatively, the FFI class should implement two different methods for the
different contexts.
This should be resolved before 7.4 is released.
Kind regards,
- Mark Clements (HappyDog)
[1] https://www.php.net/manual/en/class.ffi.php
[2] https://www.php.net/manual/en/ffi.new.php