Hey Amaury, Good points all around, but one last thing to point out, interfaces only declare what *must* be supported by an implementer, properties have no "implementation", they just are. Whereas an accessor *has* an implementation. So when you see that an interface has an accessor, you can rely on the fact that anyone who implements that interface *must* implement an accessor of the given name.
From: amaury.bouch...@gmail.com [mailto:amaury.bouch...@gmail.com] On Behalf Of Amaury Bouchard Sent: Sunday, October 14, 2012 3:23 AM To: Clint Priest Cc: Nikita Popov; Benjamin Eberlei; internals@lists.php.net Subject: Re: [PHP-DEV] [PHP-DEV [RFC] Property Accessors v1.2 You are right, we can define __get() in an interface. So, in the end I will shut my mouth. But still, it's not logical. An interface is a contract which defines the capacities of an object. If an interface defines the entry point swim(), we know that an object which implements this interface is able to swim. The goal is to define what is callable in an implementation (the basics of duck typing: if it can swim() and fly(), it's a flying fish). In PHP, it was decided that interfaces may not include member variables. I guess it's a philosophical choice; you give orders to an object, knowing what it can do (thanks to the interface). And orders are given by calling methods, not by setting properties. As I understand your explanation, you think it's normal to be able to define accessors in an interface, because it means there is some code behind. But from my point of view, the implementation (in the PHP interpreter) is not relevant; it's a design choice first. Take a look at this code: interface Fooable { public $aaa { get; set; } } class Fooer implements Fooable { public $aaa { get { /* wathever ... */ } set { /* ... you want */ } } } class Bar { public function do() { $foo = new Fooer(); $foo->aaa = 3; } } The Bar object doesn't care if $aaa is an attribute or an accessor. It is used the same way. So, if we agree that this code is correct, I understand that something like "$foo->aaa" is a valid entry point to communicate with an object through an interface. TIt means that an API is not only defined by methods. You can argue that an accessor is different from a property, but again, only Fooer knows that, Bar shouldn't have to deal with that. Then, for me there is two logical choices: - Forbid accessors in interfaces, as properties are already forbidden. - Allow accessors in interfaces => allow properties too. But it is a complete redefinition of interfaces in PHP. I saw the link you gave to me. Well, as I said before, there is a lot of good ideas in C#, but I think PHP is an opinionated language and we can do our own choices (see how namespaces work in a very different way from C++ namespaces, for example). As you point out, __get() implies the choice has already be done. So I shut up now :-) 2012/10/14 Clint Priest <cpri...@zerocue.com<mailto:cpri...@zerocue.com>> -Clint On Oct 13, 2012, at 4:21 PM, "Amaury Bouchard" <ama...@amaury.net<mailto:ama...@amaury.net>> wrote: 2012/10/13 Clint Priest <cpri...@zerocue.com<mailto:cpri...@zerocue.com>> Interfaces are used to define what methods must be present, properties are not allowed. Yes, so no one should be correct, right? I mean, yes the first declaration implies some code; but for the interface, it's still a property definition. You're mixing concepts here, it's an accessor definition, not a property definition. property != accessor, an accessor just happens to look and act like a property (which is the point of accessors). Interfaces define methods, not properties. Fine. But is an accessor (as defined in the RFC) a method? Or should we consider that an accessor definition is valid inside an interface? I would say no, because it will be used as a property: outside of the object that implements the accessor, nobody know if it's an attribute or an accessor function. It's the whole point of the RFC (apart from the asymetric visibility, but you know my point of view). So, for me, this code should be incorrect: interface Fooable { public $abc { get; set; } } Because if an object implements the interface: class Fooer implements Fooable { public $abc { get { /* what you want */ } set { /* what you want too */ } } } How this code will be used? Like that: $foo = new Fooer(); $foo->abc = 3; print($foo->abc); Everybody will agree with me that $abc is used like a property, not as a method. So the language should enforce that. There is a real issue here; this is not a fad from me. An accessor is a method and an interface which defines an accessor is indicating that the accessor must be implemented by any using the interface. See: http://msdn.microsoft.com/en-US/library/64syzecx(v=vs.80).aspx Also, "used like a property" does not mean it is a property, it is a method call with the syntax of accessing a property, it is still a method call. I believe __get() may be declared in an interface and if so, then accessors should be as well.