Proposal:
Two additional magic methods for PHP objects -
__refer(void):
Refer method is called whenever object's identifier is assigned to
variable, if such method is present.
Example:
$foo = new Bar;
$bar = $foo; //__refer invoked
Return values: null to proceed by assigning the variable to objects
identifier. Any other value returned would be assigned to variable
which is to hold the reference in case of null.
__unrefer($var):
Unrefer method would be called whenever object's identifier is about
to be replaced by anything else and would hold that something else as
argument.
Example:
$foo = new Bar;
$foo = false; //__unrefer invoked with false as argument
Return values: null to proceed with default by replacing value, false
to not to replace value and keep the reference in variable.
Real life use sample:
class SomeObject{
protected $count;
function __refer(){
$this->count++;
}
}
$foo = new Bar;
$bar = $foo;
$foobar = $bar; //SomeObject::$count = 2
class SomeCustomString{
protected $value;
function __unrefer($value){
if(is_string($value)){
$this->value = $value;
}
throw new UnexpectedValueException('This object can only hold strings');
}
}
$foo = new SomeCustomString;
$foo = 1;
Although I can't think of many uses to __refer I however can think of
one very useful use case for __unrefer - custom "types". I actually
did borrow the __unrefer functionality from SPL_Types PECL package
when trying to solve problem of how to validate contents of object
properties which are going to be set by other party and cant be
validated via set or get. I know there are ways to do this, but none
seemed pretty enough for me to actually implement.
Any feedback on this is very welcome, especially from core developers
and potential users. What would be the issues, potential drawbacks,
other?
Separate question to core developers would be, how hard it would be to
implement such functionality, or is this even possible with reasonable
effort?
Thanks, regards
Matiss Roberts Treinis <mrtreinis at gmail dot com
2013/3/19 Matīss Roberts Treinis mrtreinis@gmail.com:
Proposal:
Two additional magic methods for PHP objects -
__refer(void):
Refer method is called whenever object's identifier is assigned to
variable, if such method is present.
Example:$foo = new Bar;
$bar = $foo; //__refer invokedReturn values: null to proceed by assigning the variable to objects
identifier. Any other value returned would be assigned to variable
which is to hold the reference in case of null.__unrefer($var):
Unrefer method would be called whenever object's identifier is about
to be replaced by anything else and would hold that something else as
argument.
Example:$foo = new Bar;
$foo = false; //__unrefer invoked with false as argumentReturn values: null to proceed with default by replacing value, false
to not to replace value and keep the reference in variable.Real life use sample:
class SomeObject{
protected $count;
function __refer(){
$this->count++;
}
}$foo = new Bar;
$bar = $foo;
$foobar = $bar; //SomeObject::$count = 2
class SomeCustomString{
protected $value;
function __unrefer($value){
if(is_string($value)){
$this->value = $value;
}
throw new UnexpectedValueException('This object can only hold strings');
}
}$foo = new SomeCustomString;
$foo = 1;
Although I can't think of many uses to __refer I however can think of
one very useful use case for __unrefer - custom "types". I actually
did borrow the __unrefer functionality from SPL_Types PECL package
when trying to solve problem of how to validate contents of object
properties which are going to be set by other party and cant be
validated via set or get. I know there are ways to do this, but none
seemed pretty enough for me to actually implement.Any feedback on this is very welcome, especially from core developers
and potential users. What would be the issues, potential drawbacks,
other?
For sure: lot of overhead on any object assignments: checking
whether __refer() exist on the variable being assigned and whether
__unrefer() exist on the destination variable.
Separate question to core developers would be, how hard it would be to
implement such functionality, or is this even possible with reasonable
effort?Thanks, regards
Matiss Roberts Treinis <mrtreinis at gmail dot com
"Matīss Roberts Treinis" mrtreinis@gmail.com wrote:
Proposal:
Two additional magic methods for PHP objects -
__refer(void):
Refer method is called whenever object's identifier is assigned to
variable, if such method is present.
Example:$foo = new Bar;
$bar = $foo; //__refer invoked
This assignment is handled using PHP's copy on write mechanism for any variable. A change here has massive impact on any variable assignment, function parameter passing, ... and tons of internal places.
What we have is a hook for the objects own reference counting which is affected when an object refering to an object is used in write-context by the engine, that might easily be exteded but is rather useless. (It's trivial to create an interface or abstract base class providing this addref/delref info)
Unless you can provide a robust good patch without performance penalty in cases where this isn't used this will lead nowhere, and I doubt there is a way to come up with that. (rewriting the engine might be the closest approach)
johannes
2013/3/19 Johannes Schlüter johannes@schlueters.de
"Matīss Roberts Treinis" mrtreinis@gmail.com wrote:
Proposal:
Two additional magic methods for PHP objects -
__refer(void):
Refer method is called whenever object's identifier is assigned to
variable, if such method is present.
Example:$foo = new Bar;
$bar = $foo; //__refer invokedThis assignment is handled using PHP's copy on write mechanism for any
variable. A change here has massive impact on any variable assignment,
function parameter passing, ... and tons of internal places.What we have is a hook for the objects own reference counting which is
affected when an object refering to an object is used in write-context by
the engine, that might easily be exteded but is rather useless. (It's
trivial to create an interface or abstract base class providing this
addref/delref info)Unless you can provide a robust good patch without performance penalty in
cases where this isn't used this will lead nowhere, and I doubt there is a
way to come up with that. (rewriting the engine might be the closest
approach)johannes
I doubt my ability to rewrite engine in reasonable amount of time. With
that, I mean, lifespan of the universe at least.
However, as far as I understand, variables can currently hold values like
arrays, strings, etc, and object references. Could it be possible to add
one more possible value to this keen little list - like special type of
reference? Therefore we could only take a special care only on those
references which are known to be bound to objects which does posses __refer
and __unrefer, therefore effect on rest of the variable operations could be
brought to minimum and overhead would only affect those special objects.
Also, a little overhead is reasonable for the new functionality. It is not
like we have Pentium 2's in our DC's anymore.
However, as far as I understand, variables can currently hold values like
arrays, strings, etc, and object references. Could it be possible to add
one more possible value to this keen little list
Not without massive changes across the codebase, no. Everything touches
the zval. Changing it has far-reaching consequences.
Also, a little overhead is reasonable for the new functionality. It is not
like we have Pentium 2's in our DC's anymore.
It would have to be a critical feature that pretty much everyone would
use all the time to justify slowing down every variable assignment.
We need proposals for speeding things up by dropping rarely used
features, not proposals for slowing things down with rarely used features.
-Rasmus