Skip to content

Instantly share code, notes, and snippets.

@Seldaek
Created May 26, 2011 13:44
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Seldaek/993170 to your computer and use it in GitHub Desktop.
Save Seldaek/993170 to your computer and use it in GitHub Desktop.
Annotations

Annotation Change RFC

Most of those changes are ideas taken from the php-annotations lib (see its wiki too) by Rasmus Schultz.

Goals

I am not the author of that lib but have been discussing with him for a while and I am convinced that this could benefit Symfony users and PHP as a whole on the long run, if we standardized the annotations a bit more than what we have right now.

For example, you have to define the data type with @ORM\Column, @var and @Assert\Type(). This is absurd, if we had a proper standard way of parsing type information, and all libraries used it, it would only require one annotation. It would also save much work on the library side since they don't have to each define their own way of parsing type information, with the inevitable gaps and inconsistencies that this introduces.

Loading & Resolving

  • Annotations without namespace prefix:
    • There would be a set of standardized "autoimported" annotations (to be defined, but you can look at sample ones), e.g. @var, @param, ...
    • If they don't exist, and are not specifically autoimported or ignored, an Exception is thrown.
  • Annotations with namespace prefix (NO CHANGE):
    • The prefix is resolved using use statements.
    • If the resulting class name does not exist, an Exception is thrown.

Syntax

  • Syntax is more PHP-like, if you use @foo() whatever sits inside the parenthesis is basically what could fit inside a php array(). The syntax is equivalent to php arrays, and anything that can go in there (php constants, new Foo()) is valid.
  • Parsing of "old-style" phpdocs like @var SomeType is delegated to the annotation class itself, so the annotation can parse that how it wants. Maybe this custom parsing could be possible for () too, allowing us to support the current syntax for a transitional period, but I don't think it's a particularly good idea.
  • Nesting of annotations is not possible anymore, since this is not a valid php structure, but it seems that it's not really necessary to have nesting if we allow multiple annotations of the same name, and if you can instantiate any object to pass it to an annotation using new Foo, which seems to be the only case left in Doctrine.

Multiple Annotations & Inheritance

  • Multiple annotations of the same name are supported, optionally, the annotation defines that in its @usage annotation.
  • Rules for inheritance are described towards the end of that page and they seem good so I'm not gonna repeat everything.

Addendum

Now don't forget RFC means Request For Comments, please comment away, but don't flame. It might hurt some feelings of Annotation library developers, but please think of the users.

<?php
use Doctrine\ORM\Mapping as ORM;
use Symfony\Component\Validator\Constraints as Assert;
/**
* @ORM\Entity
*/
class AcmeUser
{
/**
* @ORM\Id
* @ORM\GeneratedValue(strategy="AUTO")
* @ORM\Column(type="integer")
*
* @var integer
*/
private $id;
/**
* @ORM\Column(type="string", nullable=false)
* @Assert\NotBlank
*
* @var string
*/
private $name;
/**
* @ORM\ManyToMany(targetEntity="Phonenumber")
* @ORM\JoinTable(name="users_phonenumbers",
* joinColumns={@ORM\JoinColumn(name="user_id", referencedColumnName="id")},
* inverseJoinColumns={@ORM\JoinColumn(name="phonenumber_id", referencedColumnName="id", unique=true)}
* )
*/
private $phonenumbers;
}
<?php
use Doctrine\ORM\Mapping as ORM;
use Symfony\Component\Validator\Constraints as Assert;
/**
* @ORM\Entity
*/
class AcmeUser
{
/**
* @ORM\Id
* @ORM\GeneratedValue("strategy"=>"AUTO") // syntax change
* @ORM\Column("type"=>"integer") // syntax change
*
* @var integer // loads Annotation\Var
*/
private $id;
/**
* @ORM\Column("type"=>"string", "nullable"=>false) // syntax change
* @Assert\NotBlank
*
* @var string // loads Annotation\Var
*/
private $name;
/**
* @ORM\ManyToMany("targetEntity"=>"Phonenumber")
* @ORM\JoinTable("name"=>"users_phonenumbers",
* "joinColumns" => new ORM\JoinColumn("user_id", array("referencedColumnName"=>"id")),
* "inverseJoinColumns" => new ORM\JoinColumn("phonenumber_id", array("referencedColumnName"=>"id", "unique"=>true))
* )
*/
private $phonenumbers;
}
@Seldaek
Copy link
Author

Seldaek commented May 27, 2011

This was just for discussion, inline comments in doc-blocks have no meaning.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment