Bug #51176 [Com]: Static calling in non-static method behaves like $this->

From: Date: Sat, 17 Aug 2013 13:59:52 +0000
Subject: Bug #51176 [Com]: Static calling in non-static method behaves like $this->
References: 1  Groups: php.bugs 
Request: Send a blank email to php-bugs+get-180950@lists.php.net to get a copy of this message
Edit report at https://bugs.php.net/bug.php?id=51176&edit=1

 ID:                 51176
 Comment by:         daniel dot ruthardt at zoesolutions dot eu
 Reported by:        majkl578 at gmail dot com
 Summary:            Static calling in non-static method behaves like
                     $this->
 Status:             Not a bug
 Type:               Bug
 Package:            Scripting Engine problem
 Operating System:   Irrelevant
 PHP Version:        5.3.2RC3
 Assigned To:        felipe
 Block user comment: N
 Private report:     N

 New Comment:

For me, the real issue is to understand the :: operator, if you do, this is absolutely 
no bug, but consistent and wanted behaviour.

To sum it all up, the :: operator tries to call the method in the current context 
(static vs. non-static) whenever possible and assumes that the current context was 
meant for non-existing methods.

----------

In details, the :: operator, does the following:

In a non-static context:

(1) Operand 1 is the context's class (via name, static or self)
	(a) if the method is (defined) non-static, it is called non-static in the 
current context
	(b) if the method is (defined) static, it is called static
	(c) if the method is not defined and __call is defined in the context’s class, 
__call is called (in the context’s class)

(2) Operand 1 is a parent class of the context's class (via name or parent)
	(a) if the method is (defined) non-static, it is called non-static in the 
current context
	(b) if the method is (defined) static, it is called static
	(c) if the method is not defined and __call is defined in the context’s class, 
a fatal error is issued
	(d) if the method is not defined and __call is defined in the parent’s class, 
__call is called (in the parent’s class)
	(e) if the method is not defined and __call is defined in the context’s class 
and in the parent’s class, __call is called in the context’s class

(3) Operand 1 is a class not related to the context
	(a) if the method is (defined) non-static, it is called non-static in the 
current context (additionally a strict standards warning is issued)
	(b) if the method is (defined) static, it is called static
	(c) if the method is not defined and __callStatic is defined in the not related 
class, __callStatic is called (in the not related class)

Observations:

(I) 2c and 2e are inconsistent. In 2c PHP wants to handle the issue in the parent 
class, whereas in 2e suddenly the issue is handled in the context’s class. I fail to 
see consistent arguments here explaining both situations.

In a static context:

(1) Operand 1 is the context’s class (via name, static or self)
	(a) if the method is (defined) static, it is called static
	(b) if the method is (defined) non-static, it is called static (additionally a 
strict standards warning is issued)
	(c) if the method is not defined and __callStatic is defined in the context’s 
class, __callStatic is called (in the context’s class)

(2) Operand 1 is a parent class of the context’s class (via name or parent)
	(a) if the method is (defined) static, it is called static
	(b) if the method is (defined) non-static, it is called static (additionally a 
strict standards warning is issued)
	(c) if the method is not defined and __callStatic is defined in the context’s 
class, a fatal error is issued
	(d) if the method is not defined and __callStatic is defined in the parent’s 
class, __callStatic is called (in the parent’s class)
	(e) if the method is not defined and __callStatic is defined in the context’s 
and in the parent’s class, __call is called in the parent’s class

(3) Operand 1 is a class not related to the context
	(a) if the method is (defined) static, it is called static
	(b) if the method is (defined) non-static, it is called static (additionally a 
strict standards warning is issued)
	(c) if the method is not defined and __callStatic is defined in the not related 
class, __callStatic is called (in the not related class)

Observations:

(I) As compared to the non-static context, 2c and 2e are consistent.


Previous Comments:
------------------------------------------------------------------------
[2011-07-29 15:57:20] steve at twitpic dot com

This is ridiculous- this bug is not bogus, it's completely legitimate, unexpected 
behavior, and totally non documented. As a reasonable programmer, one expects a 
static call to behave the same inside of a class as well as outside of a class.

How can we bring the "desired" behavior up for vote? I think that it's insane to 
not fix it.

------------------------------------------------------------------------
[2011-05-31 02:06:16] david71rj at gmail dot com

Sorry by realive this topic, but I really think that it is a bug.

If I want call "bar" with context, the correct mean is $this->bar(). Else, the 
"static" sounds for me like "call without context". I'm wrong?

Please, read this topic to understand what I'm saying: 
http://stackoverflow.com/questions/6181603/php-is-handling-incorrectly-my-static-
call

------------------------------------------------------------------------
[2010-11-03 12:03:17] majkl578 at gmail dot com

You cannot call foo::start(), because the method is non-static and therefore it does not make sense.

Also, self, static and class name are used to call methods statically, not in a object context.
For calling method bar in object context, I think '$this->' should be used instead.

Obviously parent should not behave this way and respect context, but I think it should be the only
exception (as shown in #52713).

------------------------------------------------------------------------
[2010-11-03 02:45:23] felipe@php.net

Hello, I've reverted the wrong changes introduced by trying to fix the issue reported, but
actually there is no bug at all. self::bar(), static::bar() and foo::bar() are being called in an
object context, hence the __call() is called.

I.e.
$foo->start(); // invoke the __call method
foo::start(); // invoke the __callStatic method

Thanks.

------------------------------------------------------------------------
[2010-11-03 02:35:28] felipe@php.net

Automatic comment from SVN on behalf of felipe
Revision: http://svn.php.net/viewvc/?view=revision&revision=305043
Log: - Reverted fix for bug #51176

------------------------------------------------------------------------


The remainder of the comments for this report are too long. To view
the rest of the comments, please view the bug report online at

    https://bugs.php.net/bug.php?id=51176


-- 
Edit this bug report at https://bugs.php.net/bug.php?id=51176&edit=1


Thread (12 messages)

« previous php.bugs (#180950) next »