# Annotation RFC + Patch

- Thread: https://externals.io/message/49507
- Original archive: https://news-web.php.net/php.internals/49507
- Started by Pierrick Charron on 2010-08-25T12:56:53+00:00
- Messages: 8
- 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

---

## #49507 — Pierrick Charron — 2010-08-25T12:56:53+00:00

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

Hello PHP Internals!

Recently a RFC was included on the PHP Wiki[1].
I know there've been a lot of buzz related to PHP 5.4, but this is not
the subject of this email.

I'm here to propose a new feature in PHP: Annotations.
A patch is already available with 54 tests for the moment[2].

I worked together with Guilherme Blanco to make this support happen in
a fresh PHP SVN trunk checkout.
Please review, comment and provide feedback! I think it's a very
useful support and may benefit users a lot.

[1] http://wiki.php.net/rfc/annotations
[2] http://www.adoy.net/php/Annotations.diff

Regards,
Pierrick

(Sorry if you receive this message twice but it looks like I have
problems with the ML)

---

## #49509 — Benjamin Eberlei — 2010-08-25T13:12:52+00:00

URL: https://externals.io/message/49507#49509 · In reply to: #49507

Hi Pierrick,

Awesome RFC! :) I think this is a really useful addition on many levels.

We had a chat about this yesterday, i just wanted to throw it into the
discussion here again:

I think a solution where "->getAnnotations()" returns only an array of the
annotations data is simpler to use.
Validation of the data would have to be done by the user in this case, but
you could of course
add a layer in PHP that transforms this data into an object structure.

greetings,
Benjamin

On Wed, 25 Aug 2010 08:56:53 -0400, Pierrick Charron
<pierrick@webstart.fr>
wrote:
> Hello PHP Internals!
> 
> Recently a RFC was included on the PHP Wiki[1].
> I know there've been a lot of buzz related to PHP 5.4, but this is not
> the subject of this email.
> 
> I'm here to propose a new feature in PHP: Annotations.
> A patch is already available with 54 tests for the moment[2].
> 
> I worked together with Guilherme Blanco to make this support happen in
> a fresh PHP SVN trunk checkout.
> Please review, comment and provide feedback! I think it's a very
> useful support and may benefit users a lot.
> 
> [1] http://wiki.php.net/rfc/annotations
> [2] http://www.adoy.net/php/Annotations.diff
> 
> Regards,
> Pierrick
> 
> (Sorry if you receive this message twice but it looks like I have
> problems with the ML)

---

## #49517 — Pierrick Charron — 2010-08-25T15:59:26+00:00

URL: https://externals.io/message/49507#49517 · In reply to: #49509

One of the advantage of classes vs array is that you have to create
the class and define its structure and behaviour before using it.
For example you cannot do with Array something like the [Inherited] annotation :

[Inherited]
class SampleAnnotation extends ReflectionAnnotation {}

How could you define that the SampleAnnotation annotation is Inherited
or not if you define it on the fly ?

Pierrick

2010/8/25 Benjamin Eberlei <kontakt@beberlei.de>:
>
> Hi Pierrick,
>
> Awesome RFC! :) I think this is a really useful addition on many levels.
>
> We had a chat about this yesterday, i just wanted to throw it into the
> discussion here again:
>
> I think a solution where "->getAnnotations()" returns only an array of the
> annotations data is simpler to use.
> Validation of the data would have to be done by the user in this case, but
> you could of course
> add a layer in PHP that transforms this data into an object structure.
>
> greetings,
> Benjamin
>
> On Wed, 25 Aug 2010 08:56:53 -0400, Pierrick Charron
> <pierrick@webstart.fr>
> wrote:
> > […]

---

## #49518 — Pierrick Charron — 2010-08-25T16:04:11+00:00

URL: https://externals.io/message/49507#49518

Hi Etienne,

2010/8/25 Etienne Kneuss <colder@php.net>:
> 
> > […]
>
> Quite interresting RFC! However, I've a few concerns/questions:
>
> 1) The new limitted syntax (esp. the field assignation). IMO this should
> be extended to support more/all expressions.

What kind of syntax would you like to add ? Right now you can add
common static variables, array and Annotations.

>
> 2) How does it create the annotation? will it call __construct? If so,
> Foo("asd") should defeinitely map to a constructor call, and the field
> assignation should be discarded unless we have named parameters.

Since php does not support named parameter the __construct is called
with an array as parameter
[Foo("bar", baz="baz)]
will call __construct(array("value" => "bar", "baz" => "baz));

>
> 3) What is the purpose of an aliased name?

Aliased name ?

>
> Best,
>
> > […]
>
> --
> Etienne Kneuss

---

## #49519 — Benjamin Eberlei — 2010-08-25T16:30:48+00:00

URL: https://externals.io/message/49507#49519 · In reply to: #49517

The inheritance support of annotations only affects classes am I right?
I would get rid of this stuff completely, its rather complicated and
simplify to only returning only the annotations specified on the
reflected class.

As I said before, no-one hinders you from implementing arbitrary complex
user-land annotation frameworks on top of a very simple annotations
implementation that returns simple arrays only.

For inheritance like features the user could walk the inheritance graph
from the specified child to its last super-class and `array_merge()` all
the annotations it needs.

greetings,
Benjamin

On Wed, 2010-08-25 at 11:59 -0400, Pierrick Charron wrote: 
> One of the advantage of classes vs array is that you have to create
> the class and define its structure and behaviour before using it.
> For example you cannot do with Array something like the [Inherited] annotation :
> 
> [Inherited]
> class SampleAnnotation extends ReflectionAnnotation {}
> 
> How could you define that the SampleAnnotation annotation is Inherited
> or not if you define it on the fly ?
> 
> Pierrick
> 
> 2010/8/25 Benjamin Eberlei <kontakt@beberlei.de>:
> > […]

---

## #49520 — Guilherme Blanco — 2010-08-25T16:54:00+00:00

URL: https://externals.io/message/49507#49520 · In reply to: #49518

Hi Etiene,


AliasedName is not implemented yet, but I added in RFC as one of the
first enhancements to be done.
The purpose of it is to reduce the over-typing needed to instantiate
namespaced classes.

Here is the first idea:

ReflectionAnnotation::addNamespaceAlias('Doctrine', 'Doctrine\ORM\Mapping');

[Doctrine:Entity]

would be the same to

[\Doctrine\ORM\Mapping\Entity]


The syntax can be changed, but there're some concerns to be made.

Q1 - Why not use array() instead of {} ?

The parser would consider array() as an Annotation and would attempt
to instantiate it. Also, it's not so verbose do have:

[Documentation(array("author" => "Guilherme Blanco", "age" => 26))]

Where it could be simplified to:

[Documentation({"author" = "Guilherme Blanco", "age" = 26})]


Q2- Why some keys are defined as string and others as identifiers?

The reason of the existance to identifiers are for properties of
Annotation class, whereas key strings are used for array denotation.


Q3- Why not use plain arrays as Annotations?

This would lead to a simplified EBNF, yes... but also would lead to
the lack of validation of keys, and would make Annotations accept
anything that may/may not have a meaning.
One of the main problems that PHP has is the lack of standardization;
this is one the things we tried to achieve on this implementation.
Also, more and more PHP OO is not an optional thing. I know many
projects like Drupal/Wordpress are built around functional paradigm;
but at the same time, I see no real use case to use Annotations on
functions, although we implemented this support. So... I still don't
see reasonable arguments that would justify a change to arrays.


Q4- What are the possible enhancements to be made around it?

I already added the AliasedName, mainly because I'm feeling necessity
for it already.
Another one is to send the Reflector instance in Annotation
constructor, allowing then a possible userland validation. One good
example:

PHPUnit's ExpectedException is only valid for methods. So, a possible
implementation:

namespace PHPUnit;

class ExpectedException extends \ReflectionAnnotation {
    public function __construct(\Reflector $instance, array $values) {
        if ( ! ($instance intanceof \ReflectionMethod) {
            throw new Exception('ExpectedException is only allowed in
method's scope.');
        }
        parent::__construct($instance, $values);
    }
}


Q5- Annotations separator?

Since we cannot use @, we picked from known possibilities of namespace
separator and also programming languages that have similar support.
The easiest I found is C#, which is the one we got it.




Any other questions?


> Hi Etienne,
>
> 2010/8/25 Etienne Kneuss <colder@php.net>:
> > […]
>
> What kind of syntax would you like to add ? Right now you can add
> common static variables, array and Annotations.
>
> > […]
>
> Since php does not support named parameter the __construct is called
> with an array as parameter
> [Foo("bar", baz="baz)]
> will call __construct(array("value" => "bar", "baz" => "baz));
>
> > […]
>
> Aliased name ?
>
> > […]
>
> --
> 
> 
>
>



-- 
Guilherme Blanco
Mobile: +55 (16) 9215-8480
MSN: guilhermeblanco@hotmail.com
São Paulo - SP/Brazil

---

## #49523 — Christian Kaps — 2010-08-25T18:22:15+00:00

URL: https://externals.io/message/49507#49523 · In reply to: #49518

Hi,

I love this RFC. But I have a view questions.

1.
> Since php does not support named parameter the __construct is called
> with an array as parameter
> [Foo("bar", baz="baz)]
> will call __construct(array("value" => "bar", "baz" => "baz));
>

I am a absolute C noob but I have implemented named and unnamed
exceptions in userland. So it should also be possible in C, or not!? Are
the names from the constructor parameters not available through the
reflection API? This may be a little bit more overhead but I think
unnamed annotations are very useful.

[URL('http://www.php.net', 'PHP', 'blank')] or
[URL('http://www.php.net', 'PHP')] or
[URL('url' = 'http://www.php.net', 'name' = 'PHP', 'target' = 'blank')]

class URL extends ReflectionAnnotation {

    public function __construct($url, $name, $target = 'self') {

    }
}

instead of

[URL('url' = 'http://www.php.net', 'name' = 'PHP', 'target' = 'blank')]

class URL extends ReflectionAnnotation {

    public $url;

    public $title;

    public $target = 'self';

    public function __construct($params) {

    }
}

For me an additional point for providing unnamed annotations is the
possibility to use type hinting. So it isn't possible to pass an integer
when an array is expected. I know I can validate the parameters in the
constructor. But this is additional work.

2. Is it possible to use nested annotations and what is the syntax?

3.
> AliasedName is not implemented yet, but I added in RFC as one of the
> first enhancements to be done.
> The purpose of it is to reduce the over-typing needed to instantiate
> namespaced classes.
>
> Here is the first idea:
>
> ReflectionAnnotation::addNamespaceAlias('Doctrine', 'Doctrine\ORM\Mapping');
>
> [Doctrine:Entity]
>
> would be the same to
>
> [\Doctrine\ORM\Mapping\Entity]

Is it possible to define a use statement for an annotation instead of
defining the namespace alias over the reflection API?

namespace com\mohiva\framework\cache;

use com\mohiva\framework\annotations\File;

[File('/path/to/the/file')]

Greetings,
Christian

---

## #49552 — Kalle Sommer Nielsen — 2010-08-28T00:19:45+00:00

URL: https://externals.io/message/49507#49552 · In reply to: #49507

Hi Pierrick, Guilherme

2010/8/25 Pierrick Charron <pierrick@webstart.fr>:
> I'm here to propose a new feature in PHP: Annotations.
> A patch is already available with 54 tests for the moment[2].
>
> I worked together with Guilherme Blanco to make this support happen in
> a fresh PHP SVN trunk checkout.
> Please review, comment and provide feedback! I think it's a very
> useful support and may benefit users a lot.

After looking over both the RFC and patch I think its a great feature,
and its something I remember Guilherme have bugged about since 5.3's
development stage ;-).

The syntax for one is decent, by having it in the code rather than a
source code comment and its somewhat compatible with that in C#. The
only thing I could see missing in the patch, although its a minor
thing is to dump Annotations when doing something like:
Reflection::export(new Reflection...(...)); and your small TODO in
ReflectionAnnotation::__construct() :)

But I'm a +1 for merging this into trunk, as it will without doubt get
improved as we go, like with Traits.

-- 
regards,

Kalle Sommer Nielsen
kalle@php.net
