# RFC Proposal - Attributes read/write visibility

- Thread: https://externals.io/message/61246
- Original archive: https://news-web.php.net/php.internals/61246
- Started by Amaury Bouchard on 2012-07-15T15:46:08+00:00
- Messages: 17
- 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

---

## #61246 — Amaury Bouchard — 2012-07-15T15:46:08+00:00

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

Hi,

Here is an RFC proposal about a syntax extension for PHP. The purpose is to
manage precisely the visbiliy of attributes, by separating reading and
writing access.

First of all, I know there is already an RFC about attributes ("Property
get/set syntax" [1]). Its goal is mainly different, but I'll discuss it
lower.


THE PROBLEM
In my experience, one of the major usage of getters is when you want to
have an attribute, readable (but not writable) from outside the object.
More, the attribute's visibilty is then chosen between private and
protected, depending on your inheritance design.

The result is not really satisfying:
1. You have to write getter's code. Maybe, it's just a simple return, but
every line of code should be useful, not a workaround.
2. You ended with 2 syntaxes; $obj->attr when the attribute is public, but
$obj->getAttr() when you must use a getter. It's a bit schizophrenic.


THE IDEA
I suggest to be able to separate reading visibility and writing visibility,
using a colon to separate them. If only one visibility is given, it will be
used for both reading and writing access.

For example:
class A {
    public $a;           // public reading, public writing
    public:public $b;    // the same
    public:protected $c; // public reading, protected writing
    public:private $d;   // public reading, private writing
    public:const $e;     // public reading, no writing allowed

    protected $f;           // protected reading, protected writing
    protected:protected $g; // the same
    protected:private $h;   // protected reading, private writing
    protected:const $i;     // protected reading, no writing allowed

    private $j;         // private reading, private writing
    private:private $k; // the same
    private:const $l;   // private reading, no writing allowed
}

As you can see, I think that writing access should be more restrictive than
reading access (or equivalent to it). A "private:public" visibility would
make no sense.


SOURCE CODE
I did a patch. It kinda works, but I'm still working on it (because I'm
still learning Zend Engine's internals).
The code on GitHub: https://github.com/Amaury/php-src
All advises are welcome.


PRIOR WORK
As I said before, the "Property get/set syntax" RFC is in discussion. My
proposal doesn't focus on the same goals, but they could be fully
compatible.

Thus, we would be able to write this kind of code:
class A {
    // $str has public reading and private writing,
    // and manage french quotes
    public:private $str {
        get { return "«" . $this->str . "»"; }
        set { $this->str = trim($value, "«»"); }
    }
}

Maybe you saw that the "Property get/set syntax" RFC has an intended syntax
for read-only and write-only attributes. From my point of view, there is a
deep and clean separation between a getter/setter syntax and an extended
visibility syntax. It shouldn't be in the same RFC.
More, the proposed "read-only" and "write-only" keywords are less precise
and powerful than what I'm suggesting.


I would be happy to discuss all that with you guys.

Best regards,

Amaury Bouchard


[1] : https://wiki.php.net/rfc/propertygetsetsyntax-as-implemented

---

## #61248 — Brandon Wamboldt — 2012-07-15T15:50:11+00:00

URL: https://externals.io/message/61246#61248 · In reply to: #61246

This seems pretty useful, but could technically be accomplished using the
get/set syntax already proposed. Obviously this is a cleaner implementation
however.



> Hi,
>
> Here is an RFC proposal about a syntax extension for PHP. The purpose is to
> manage precisely the visbiliy of attributes, by separating reading and
> writing access.
>
> First of all, I know there is already an RFC about attributes ("Property
> get/set syntax" [1]). Its goal is mainly different, but I'll discuss it
> lower.
>
>
> THE PROBLEM
> In my experience, one of the major usage of getters is when you want to
> have an attribute, readable (but not writable) from outside the object.
> More, the attribute's visibilty is then chosen between private and
> protected, depending on your inheritance design.
>
> The result is not really satisfying:
> 1. You have to write getter's code. Maybe, it's just a simple return, but
> every line of code should be useful, not a workaround.
> 2. You ended with 2 syntaxes; $obj->attr when the attribute is public, but
> $obj->getAttr() when you must use a getter. It's a bit schizophrenic.
>
>
> THE IDEA
> I suggest to be able to separate reading visibility and writing visibility,
> using a colon to separate them. If only one visibility is given, it will be
> used for both reading and writing access.
>
> For example:
> class A {
>     public $a;           // public reading, public writing
>     public:public $b;    // the same
>     public:protected $c; // public reading, protected writing
>     public:private $d;   // public reading, private writing
>     public:const $e;     // public reading, no writing allowed
>
>     protected $f;           // protected reading, protected writing
>     protected:protected $g; // the same
>     protected:private $h;   // protected reading, private writing
>     protected:const $i;     // protected reading, no writing allowed
>
>     private $j;         // private reading, private writing
>     private:private $k; // the same
>     private:const $l;   // private reading, no writing allowed
> }
>
> As you can see, I think that writing access should be more restrictive than
> reading access (or equivalent to it). A "private:public" visibility would
> make no sense.
>
>
> SOURCE CODE
> I did a patch. It kinda works, but I'm still working on it (because I'm
> still learning Zend Engine's internals).
> The code on GitHub: https://github.com/Amaury/php-src
> All advises are welcome.
>
>
> PRIOR WORK
> As I said before, the "Property get/set syntax" RFC is in discussion. My
> proposal doesn't focus on the same goals, but they could be fully
> compatible.
>
> Thus, we would be able to write this kind of code:
> class A {
>     // $str has public reading and private writing,
>     // and manage french quotes
>     public:private $str {
>         get { return "«" . $this->str . "»"; }
>         set { $this->str = trim($value, "«»"); }
>     }
> }
>
> Maybe you saw that the "Property get/set syntax" RFC has an intended syntax
> for read-only and write-only attributes. From my point of view, there is a
> deep and clean separation between a getter/setter syntax and an extended
> visibility syntax. It shouldn't be in the same RFC.
> More, the proposed "read-only" and "write-only" keywords are less precise
> and powerful than what I'm suggesting.
>
>
> I would be happy to discuss all that with you guys.
>
> Best regards,
>
> Amaury Bouchard
>
>
> [1] : https://wiki.php.net/rfc/propertygetsetsyntax-as-implemented
>



-- 
*Brandon Wamboldt*
Programmer / Web Developer

StackOverflow Careers
Profile<http://careers.stackoverflow.com/brandonwamboldt>- GitHub
Profile <https://github.com/brandonwamboldt> -
LinkedIn<https://github.com/brandonwamboldt> -
My Blog <http://brandonwamboldt.ca/

---

## #61251 — Amaury Bouchard — 2012-07-15T18:13:17+00:00

URL: https://externals.io/message/61246#61251 · In reply to: #61248

2012/7/15 Brandon Wamboldt <brandon.wamboldt@gmail.com>

> This seems pretty useful, but could technically be accomplished using the
> get/set syntax already proposed. Obviously this is a cleaner implementation
> however.


As I said, the get/set syntax RFC propose a "read-only" and a "write-only"
keywords.
For example, it will not allow you to have an attribute readable only by
descendant classes (and by the current class, of course), and at the same
time only writable by the current class.

PHP is an object-oriented language with public/protected private
visibility. Visibility conveys meanings, and we shouldn't loose these
meanings when we add new functionalities.

Once again, the purpose of the get/set syntax RFC is to define getters and
setters directly where attributes are defined. Attributes' visibility is a
distinct question, which deserve a distinct answer (even if there is some
obvious connections).



>
> > […]
>
>
>
> --
> *Brandon Wamboldt*
> Programmer / Web Developer
>
> StackOverflow Careers Profile<http://careers.stackoverflow.com/brandonwamboldt>- GitHub
> Profile <https://github.com/brandonwamboldt> - LinkedIn<https://github.com/brandonwamboldt> -
> My Blog <http://brandonwamboldt.ca/

---

## #61292 — Nikita Popov — 2012-07-16T13:11:55+00:00

URL: https://externals.io/message/61246#61292 · In reply to: #61246

> Hi,
>
> Here is an RFC proposal about a syntax extension for PHP. The purpose is to
> manage precisely the visbiliy of attributes, by separating reading and
> writing access.
>
> First of all, I know there is already an RFC about attributes ("Property
> get/set syntax" [1]). Its goal is mainly different, but I'll discuss it
> lower.

I'm not sure I really understand what this adds over the existing
getter/setter proposal. read-only and write-only should cover the most
common cases. If you do need visibility control, it is possible too:

public $property {
    get { ... }
    protected set { ... }
}

So what does this proposal add to it?

Nikita

---

## #61293 — Andrew Faulds — 2012-07-16T13:20:05+00:00

URL: https://externals.io/message/61246#61293 · In reply to: #61292

An ugly, confusion-causing syntax.


> 
> > […]
>
> I'm not sure I really understand what this adds over the existing
> getter/setter proposal. read-only and write-only should cover the most
> common cases. If you do need visibility control, it is possible too:
>
> public $property {
>     get { ... }
>     protected set { ... }
> }
>
> So what does this proposal add to it?
>
> Nikita
>
> --
> 
> 
>



-- 
Andrew Faulds (AJF)
http://ajf.me/

---

## #61311 — Amaury Bouchard — 2012-07-16T15:24:52+00:00

URL: https://externals.io/message/61246#61311 · In reply to: #61292

2012/7/16 Nikita Popov <nikita.ppv@gmail.com>

> I'm not sure I really understand what this adds over the existing
> getter/setter proposal. read-only and write-only should cover the most
> common cases. If you do need visibility control, it is possible too:
>
> public $property {
>     get { ... }
>     protected set { ... }
> }
>
> So what does this proposal add to it?
>
>
Yes, but only if you have to write an accessor.
If you just want an attribute that is:
- readable from everywhere
- writable from the current class only

With my syntax:
    public:private $a;  (read it aloud "public reading, private writing")

With the existing RFC:
    public $a {
        private set { $this->a = $value; }
    }

Which one is better? Why should I write code for that?

If you read the existing RFC, you'll see that all examples involve a
specific case: when you have a "fake" attribute, which manipulates date
stored in other attributes. The given example is an $Hours attributes,
which is calculated from the private $Seconds attribute.
Again, it could be very useful. But it doesn't work all the time.

---

## #61312 — Daniel Macedo — 2012-07-16T15:25:35+00:00

URL: https://externals.io/message/61246#61312 · In reply to: #61293

You already have the read-only/write-only option proposed on that RFC
- by not defining set and vice-versa for write only - or by inserting
new keywords (not sure if this is needed/optimal).

And nowhere in PHP do we have the syntax you propose as A:B, and I
even recall a short array [a:1, b:2] syntax from being promptly
rejected in the past, although I can't recall the argument against it.

Plus that RFC can allow for additional implementation of something
like a lambda/other function calls; a lot of things way more
useful/interesting to see than just controlling visibility.

---

## #61313 — Andrew Faulds — 2012-07-16T15:26:36+00:00

URL: https://externals.io/message/61246#61313 · In reply to: #61311

How much syntactic sugar do we really need? Why add two ways to do something?


> 2012/7/16 Nikita Popov <nikita.ppv@gmail.com>
>
> > […]
> Yes, but only if you have to write an accessor.
> If you just want an attribute that is:
> - readable from everywhere
> - writable from the current class only
>
> With my syntax:
>     public:private $a;  (read it aloud "public reading, private writing")
>
> With the existing RFC:
>     public $a {
>         private set { $this->a = $value; }
>     }
>
> Which one is better? Why should I write code for that?
>
> If you read the existing RFC, you'll see that all examples involve a
> specific case: when you have a "fake" attribute, which manipulates date
> stored in other attributes. The given example is an $Hours attributes,
> which is calculated from the private $Seconds attribute.
> Again, it could be very useful. But it doesn't work all the time.



-- 
Andrew Faulds (AJF)
http://ajf.me/

---

## #61314 — Nikita Popov — 2012-07-16T15:29:57+00:00

URL: https://externals.io/message/61246#61314 · In reply to: #61311

> Yes, but only if you have to write an accessor.
> If you just want an attribute that is:
> - readable from everywhere
> - writable from the current class only
>
> With my syntax:
>     public:private $a;  (read it aloud "public reading, private writing")
>
> With the existing RFC:
>     public $a {
>         private set { $this->a = $value; }
>     }
>
> Which one is better? Why should I write code for that?
>
> If you read the existing RFC, you'll see that all examples involve a
> specific case: when you have a "fake" attribute, which manipulates date
> stored in other attributes. The given example is an $Hours attributes, which
> is calculated from the private $Seconds attribute.
> Again, it could be very useful. But it doesn't work all the time.

You can also just write public $a { get; private set; }. I see that
the syntax is a bit more verbose, but I definitely prefer it to the
obscure public:private notation. With the getters/setters the meaning
is somewhat clear (public get, private set), with the colon notation
it isn't really clear.

Nikita

---

## #61315 — Daniel Macedo — 2012-07-16T15:30:15+00:00

URL: https://externals.io/message/61246#61315 · In reply to: #61311

> If you just want an attribute that is:
> - readable from everywhere
> - writable from the current class only

I believe the RFC sugests:

public $a {
    private set;
}

Would be enough, if I understand correctly...

---

## #61317 — Amaury Bouchard — 2012-07-16T15:31:43+00:00

URL: https://externals.io/message/61246#61317 · In reply to: #61313

My point is not to add two ways to do the same thing.
What I'm humbly suggesting to do is to keep the core idea of the existing
RFC (make things easier when you have to write getters/setters), and think
about another syntax for managing reading and writing visibilities.


2012/7/16 Andrew Faulds <ajfweb@googlemail.com>

> How much syntactic sugar do we really need? Why add two ways to do
> something?
>
> 
> > […]
>
>
>
> --
> Andrew Faulds (AJF)
> http://ajf.me/

---

## #61318 — Daniel Macedo — 2012-07-16T15:38:39+00:00

URL: https://externals.io/message/61246#61318 · In reply to: #61317

> My point is not to add two ways to do the same thing.
> What I'm humbly suggesting to do is to keep the core idea of the existing
> RFC (make things easier when you have to write getters/setters), and think
> about another syntax for managing reading and writing visibilities.
>

The thing is that coming down to two options of a new A:B syntax or
the RFC proposal, the RFC fits on the current syntax and allows for
more flexibility such as expanding with other function calls, I think
that would get the support+votes behind it.

The only thing I'm not yet particulartly fond of in this RFC is the
$value variable, but I guess there might not be another way around it,
unless we go for a more complex syntax.

---

## #61319 — Amaury Bouchard — 2012-07-16T15:41:50+00:00

URL: https://externals.io/message/61246#61319 · In reply to: #61314

Are you sure that this mix of distributed visibilities (sometimes before
the attribute, sometimes before a "get" or "set" keyword) and new keywords
("read-only" and "write-only", between the initial visibility and the
attribute itself; but what is an "initial visibility" exactly?) is really
more clear?

Take this code, for instance:
    public read-only $a {
        protected get;
        private set;
    }

Yeah, I know, the "public" should be "protected". But in some years, when
you'll have some legacy code, I'm pretty sure we will see this kind of
code. It should work, the "public" visibility is just overloaded by the
"protected" and "private" visibilities. Anyway, it's perturbing.
Oh, and there is a "read-only" keyword. Damned, I added a private setter, I
forgot it was read-only and I forgot to remove it...

So, I guess it should be like that:
    protected $a {
        private set;
    }

Then, try to read this code aloud. I'm really not sure it's better than a
simple "protected:private $a;", which could be read like "protected
reading, private writing".


2012/7/16 Nikita Popov <nikita.ppv@gmail.com>

> On Mon, Jul 16, 2012 at 5:24 PM, Amaury Bouchard <amaury@amaury.net>
> wrote:
> > […]
> which
> > […]
>
> You can also just write public $a { get; private set; }. I see that
> the syntax is a bit more verbose, but I definitely prefer it to the
> obscure public:private notation. With the getters/setters the meaning
> is somewhat clear (public get, private set), with the colon notation
> it isn't really clear.
>
> Nikita

---

## #61321 — Daniel Macedo — 2012-07-16T15:57:22+00:00

URL: https://externals.io/message/61246#61321 · In reply to: #61319

That is already accounted for, both the visibility (what's inside
limits what's before the variable) as well as changing the
write-only/read-only options. If you read the RFC, when extending a
class and adding "set" method to a member that was read-only, you
overload the read-only setting...

Hence on the example you gave I expect the set method to be available
privately, and the visibility to be decreased from public to
protected.

Might not make a lot of sense to have it all together (even on legacy
code - you do review before committing, right? :), but it's accounted
for when extending classes.

---

## #61589 — Matthew Weier O'Phinney — 2012-07-20T22:48:03+00:00

URL: https://externals.io/message/61246#61589 · In reply to: #61317

> --f46d0446312cc5e06104c4f42161
> Content-Type: text/plain; charset=ISO-8859-1
>
> My point is not to add two ways to do the same thing.
> What I'm humbly suggesting to do is to keep the core idea of the
> existing RFC (make things easier when you have to write
> getters/setters), and think about another syntax for managing reading
> and writing visibilities.

My first impression, being familiar with the other proposal, was that
this looked like duplication. However, on looking at the examples, I
have to admit that I really like the approach -- in many cases, it
obviates the need for a getter entirely. It would help dry up a lot of
code, reduce the number of method calls overall, and still enforce
internal logic when setting the value in the first place.

I like it; it feels elegant.


> 2012/7/16 Andrew Faulds <ajfweb@googlemail.com>
>
> > […]
>
> --f46d0446312cc5e06104c4f42161--


-- 
Matthew Weier O'Phinney
Project Lead            | matthew@zend.com
Zend Framework          | http://framework.zend.com/
PGP key: http://framework.zend.com/zf-matthew-pgp-key.asc

---

## #61590 — Matthew Weier O'Phinney — 2012-07-20T22:48:05+00:00

URL: https://externals.io/message/61246#61590 · In reply to: #61293

> An ugly, confusion-causing syntax.

I'm sorry, but how does this add _anything_ to the discussion?

Qualify your statement, please. What do you find "ugly" about the
syntax, and why? Where do you see confusion arising from the syntax -
what problems do you foresee arising?

Making judgmental statements without any context like the one you made
above does nobody any good, and if you can't find the time to qualify
them properly, it'd be better for everybody if you simply didn't post.

</end rant>

> 
> > […]
>
>
>


-- 
Matthew Weier O'Phinney
Project Lead            | matthew@zend.com
Zend Framework          | http://framework.zend.com/
PGP key: http://framework.zend.com/zf-matthew-pgp-key.asc

---

## #61616 — Amaury Bouchard — 2012-07-21T11:32:57+00:00

URL: https://externals.io/message/61246#61616 · In reply to: #61589

Thank you Matthew. I had the feeling that my proposal was dismissed a bit
quickly by some people, while I think it's how object-oriented languages
should handle attributes' visibility.
I still think it's very simple and elegant, and more coherent in some
situations (those situations targeted by the proposal).


I would like everybody give 5 minutes to this idea [1]   :-)

[1] : http://37signals.com/svn/posts/3124-give-it-five-minutes


2012/7/21 Matthew Weier O'Phinney <weierophinney@php.net>

> 
> > […]
>
> My first impression, being familiar with the other proposal, was that
> this looked like duplication. However, on looking at the examples, I
> have to admit that I really like the approach -- in many cases, it
> obviates the need for a getter entirely. It would help dry up a lot of
> code, reduce the number of method calls overall, and still enforce
> internal logic when setting the value in the first place.
>
> I like it; it feels elegant.
>
>
> > […]
> most
> > […]
> writing")
> > […]
> date
> > […]
>
>
> --
> Matthew Weier O'Phinney
> Project Lead            | matthew@zend.com
> Zend Framework          | http://framework.zend.com/
> PGP key: http://framework.zend.com/zf-matthew-pgp-key.asc
