# Magic method visibility in PHP 5.3+

- Thread: https://externals.io/message/38694
- Original archive: https://news-web.php.net/php.internals/38694
- Started by Ralph Schindler on 2008-07-01T22:55:49+00:00
- Messages: 5
- Reply by email to internals@lists.php.net
- More for agents: search with https://externals.io/search.md?q={query} · JSON API at https://externals.io/api · documentation at https://externals.io/llms.txt

---

## #38694 — Ralph Schindler — 2008-07-01T22:55:49+00:00

URL: https://externals.io/message/38694#38694

Well, I guess I blinked and missed the internal@ thread on this topic :)

Seriously though, if there was a thread on this subject, please point me 
in the right direction.

In PHP 5.3 snaps, it appears that magic methods __isset, __unset, __get, 
__set must have a public visibility or the engine will trigger a 
warning.  Why is this?  It works as expected in 5.x branches.

I am not sure why this should be enforced as it should be up to the 
developer as to which methods in the API should be exposed for direct 
invocation.

If a developer never intends on a user calling $obj->__set(...), then it 
should be allowed that the public call to that method be disallowed, but 
still allow the magic functionality (b/c of the presence of that magic 
function.)

Without getting too long winded, ill just put code and warnings below.

Cheers,
Ralph Schindler




script.php

<?php

class SomeMagic
{

     public static function getInstance() {}
     protected function __construct() { }
     protected function __isset($name){}
     protected function __unset($name){}
     protected function __set($name, $value){}
     protected function __get($name) {}
     protected function __clone() {}
     protected function __destruct() {}

}

Warnings:

$ /usr/local/php53/bin/php test-magicaccess.php
PHP Warning:  The magic method __isset() must have public visibility and 
can not be static in script.php on line 8
PHP Warning:  The magic method __unset() must have public visibility and 
can not be static in script.php on line 9
PHP Warning:  The magic method __set() must have public visibility and 
can not be static in script.php on line 10
PHP Warning:  The magic method __get() must have public visibility and 
can not be static in script.php on line 11

---

## #38695 — Stanislav Malyshev — 2008-07-01T23:18:49+00:00

URL: https://externals.io/message/38694#38695 · In reply to: #38694

Hi!

> In PHP 5.3 snaps, it appears that magic methods __isset, __unset, __get, 
> __set must have a public visibility or the engine will trigger a 
> warning.  Why is this?  It works as expected in 5.x branches.

I think it doesn't actually work as expected - because as far as I can 
see, visibility is ignored on these methods. Consider this code:

class Foo {
         private function __get($name) {
                 return 42;
         }
}

$z = new Foo();
echo $z->bar;

On 5.2, it happily prints 42, even though you should not have access to 
__get from outside the class, if it were true "private". Having 
"private" there actually is somewhat misleading - while it looks like 
internal API and thus can be changed by the class developer at will or 
dropped altogether, it is actually a public API which is exposed to the 
client.

> I am not sure why this should be enforced as it should be up to the 
> developer as to which methods in the API should be exposed for direct 
> invocation.

I don't think magic methods are meant to be directly invoked. That's why 
they are magic ;) In any case, since these methods are invoked in 
"magic" way anyway, regardless of visibility, putting non-public 
visibility on them makes little sense and actually makes people think 
they can not be invoked from outside of the class - while it is not the 
case, they can. Thus, even if there was no warning, I'd recommend never 
putting non-public visibility on them.
-- 
Stanislav Malyshev, Zend Software Architect
stas@zend.com   http://www.zend.com/
(408)253-8829   MSN: stas@zend.com

---

## #38699 — Lokrain — 2008-07-02T07:21:28+00:00

URL: https://externals.io/message/38694#38699 · In reply to: #38695

Hello there,

I don't have enough time to write more detailed example, but I still want to
write my opinion.

I totally agree with Stanislav, because for me magic functions should be
used in last leaf of some class extend tree. They are some kind of feature
when you are producing the non-framework, specific project coding stuff.
Which mean they should be not encapsulated and invisible.

If a developer never intends on a user calling $obj->__set(...), then it
> should be allowed that the public call to that method be disallowed, but
> still allow the magic functionality (b/c of the presence of that magic
> function.)
>

Giving the "user" ability to call $obj->__set() is just some kind of speed
optimization, you just miss the magic thing. Another point of view is that
this __set() is still a function why you want to disable the function calls
and enable the functionality? B/c of the presence of that magic function?
What a drama! This is not fairy world where magic should be wonderful thing
which just happens. Think of us (developers) as wizards, who know how/why
this magic works!

Nothing personal just some thoughts.

Regards, Dimitar Isusov

---

## #38702 — Daniel Convissor — 2008-07-02T15:17:33+00:00

URL: https://externals.io/message/38694#38702 · In reply to: #38694

> In PHP 5.3 snaps, it appears that magic methods __isset, __unset, __get, 
> __set must have a public visibility or the engine will trigger a 
> warning.  Why is this?  It works as expected in 5.x branches.

Because that's what the manual says it should do.  And there are 
technical reasons outlined by others here already.  Here is the internals 
discussion about getting things straight:
http://news.php.net/php.internals/36813

Thanks,

--Dan

-- 
 T H E   A N A L Y S I S   A N D   S O L U T I O N S   C O M P A N Y
            data intensive web and database programming
                http://www.AnalysisAndSolutions.com/
 4015 7th Ave #4, Brooklyn NY 11232  v: 718-854-0335 f: 718-854-0409

---

## #38744 — crrodriguez@suse.de — 2008-07-04T02:23:42+00:00

URL: https://externals.io/message/38694#38744 · In reply to: #38702

Daniel Convissor escribió:

> Because that's what the manual says it should do.  

Right, however I disagree with the fact it is a warning, it should be a 
fatal error IMHO.


-- 
"A computer is like an Old Testament god, with a lot of rules and no 
mercy. "

Cristian Rodríguez R.
Platform/OpenSUSE - Core Services
SUSE LINUX Products GmbH
Research & Development
http://www.opensuse.org/
