@@ -11,36 +11,42 @@ type guessers.
1111
1212.. sidebar :: Form Type Guessers in the Bridges
1313
14- Symfony also provides some form type guessers in the bridges. These can be
15- used if you use that library.
14+ Symfony also provides some form type guessers in the bridges:
1615
1716 * :class: `Symfony\\ Bridge\\ Propel1\\ Form\\ PropelTypeGuesser ` provided by
1817 the Propel1 bridge;
1918 * :class: `Symfony\\ Bridge\\ Doctrine\\ Form\\ DoctrineOrmTypeGuesser `
2019 provided by the Doctrine bridge.
2120
22- A PHPDoc Type Guesser
23- ---------------------
21+ Create a PHPDoc Type Guesser
22+ ----------------------------
2423
25- In this section, you are going to build a PHPDoc type guesser. At first, you
26- need to create a class which extends
27- :class: `Symfony\\ Component\\ Form\\ FormTypeGuesserInterface `. This interface
28- requires 4 methods:
24+ In this section, you are going to build a guesser that reads information about
25+ fields from the PHPDoc of the properties. At first, you need to create a class
26+ which implements :class: `Symfony\\ Component\\ Form\\ FormTypeGuesserInterface `.
27+ This interface requires 4 methods:
2928
3029* :method: `Symfony\\ Component\\ Form\\ FormTypeGuesserInterface::guessType ` -
3130 tries to guess the type of a field;
3231* :method: `Symfony\\ Component\\ Form\\ FormTypeGuesserInterface::guessRequired ` -
33- tries to guess the value of the ``required `` option;
32+ tries to guess the value of the :ref: `required <reference-form-option-required >`
33+ option;
3434* :method: `Symfony\\ Component\\ Form\\ FormTypeGuesserInterface::guessMaxLength ` -
35- tries to guess the value of the ``max_length `` option;
35+ tries to guess the value of the :ref: `max_length <reference-form-option-max_length >`
36+ option;
3637* :method: `Symfony\\ Component\\ Form\\ FormTypeGuesserInterface::guessPattern ` -
37- tries to guess the value of the ``pattern `` option.
38+ tries to guess the value of the :ref: `pattern <reference-form-option-pattern >`
39+ option.
3840
39- The most basic class looks like::
41+ Start by creating the class and these methods. Next, you'll learn how to fill each on.
42+
43+ .. code-block :: php
44+
45+ namespace Acme\Form;
4046
4147 use Symfony\Component\Form\FormTypeGuesserInterface;
4248
43- class PHPDocTypeGuesser implements FormTypeGuesserInterface
49+ class PhpdocTypeGuesser implements FormTypeGuesserInterface
4450 {
4551 public function guessType($class, $property)
4652 {
@@ -69,54 +75,70 @@ that the type guesser cannot guess the type.
6975The ``TypeGuess `` constructor requires 3 options:
7076
7177* The type name (one of the :doc: `form types </reference/forms/types `);
72- * Additionally options (for instance, when the type is ``entity ``, you also
78+ * Additional options (for instance, when the type is ``entity ``, you also
7379 want to set the ``class `` option). If no types are guessed, this should be
7480 set to an empty array;
7581* The confidence that the guessed type is correct. This can be one of the
7682 constants of the :class: `Symfony\\ Component\\ Form\\ Guess\G uess ` class:
7783 ``LOW_CONFIDENCE ``, ``MEDIUM_CONFIDENCE ``, ``HIGH_CONFIDENCE ``,
78- ``VERY_HIGH_CONFIDENCE ``. After all type guessers are executed, the type
79- with the highest confidence is used.
84+ ``VERY_HIGH_CONFIDENCE ``. After all type guessers have been executed, the
85+ type with the highest confidence is used.
8086
8187With this knowledge, you can easily implement the ``guessType `` method of the
8288``PHPDocTypeGuesser ``::
8389
90+ namespace Acme\Form;
91+
8492 use Symfony\Component\Form\Guess\Guess;
8593 use Symfony\Component\Form\Guess\TypeGuess;
8694
87- // ...
88- public function guessType($class, $property)
95+ class PhpdocTypeGuesser implements FormTypeGuesserInterface
8996 {
90- $annotations = $this->readPhpDocAnnotations($class, $property);
91-
92- if (!isset($annotations['var'])) {
93- return; // guess nothing if the @var annotation is not available
97+ public function guessType($class, $property)
98+ {
99+ $annotations = $this->readPhpDocAnnotations($class, $property);
100+
101+ if (!isset($annotations['var'])) {
102+ return; // guess nothing if the @var annotation is not available
103+ }
104+
105+ // otherwise, base the type on the @var annotation
106+ switch ($annotations['var']) {
107+ case 'string':
108+ // there is a high confidence that the type is a string when
109+ // @var string is used
110+ return new TypeGuess('text', array(), Guess::HIGH_CONFIDENCE);
111+
112+ case 'int':
113+ case 'integer':
114+ // integers can also be the id of an entity or a checkbox (0 or 1)
115+ return new TypeGuess('integer', array(), Guess::MEDIUM_CONFIDENCE);
116+
117+ case 'float':
118+ case 'double':
119+ case 'real':
120+ return new TypeGuess('number', array(), Guess::MEDIUM_CONFIDENCE);
121+
122+ case 'boolean':
123+ case 'bool':
124+ return new TypeGuess('checkbox', array(), Guess::HIGH_CONFIDENCE);
125+
126+ default:
127+ // there is a very low confidence that this one is correct
128+ return new TypeGuess('text', array(), Guess::LOW_CONFIDENCE);
129+ }
94130 }
95131
96- // otherwise, base the type on the @var annotation
97- switch ($annotations['var']) {
98- case 'string':
99- // there is a high confidence that the type is a string when
100- // @var string is used
101- return new TypeGuess('text', array(), Guess::HIGH_CONFIDENCE);
102-
103- case 'int':
104- case 'integer':
105- // integers can also be the id of an entity or a checkbox (0 or 1)
106- return new TypeGuess('integer', array(), Guess::MEDIUM_CONFIDENCE);
107-
108- case 'float':
109- case 'double':
110- case 'real':
111- return new TypeGuess('number', array(), Guess::MEDIUM_CONFIDENCE);
112-
113- case 'boolean':
114- case 'bool':
115- return new TypeGuess('checkbox', array(), Guess::HIGH_CONFIDENCE);
116-
117- default:
118- // there is a very low confidence that this one is correct
119- return new TypeGuess('text', array(), Guess::LOW_CONFIDENCE);
132+ protected function readPhpDocAnnotations($class, $property)
133+ {
134+ $reflectionProperty = new \ReflectionProperty($class, $property);
135+ $phpdoc = $reflectionProperty->getDocComment();
136+
137+ // parse the $phpdoc into an array like:
138+ // array('type' => 'string', 'since' => '1.0')
139+ $phpdocTags = ...;
140+
141+ return $phpdocTags;
120142 }
121143 }
122144
@@ -139,10 +161,10 @@ set.
139161
140162.. caution ::
141163
142- You should be very careful with the ``guessPattern `` method. When the
164+ You should be very careful using the ``guessPattern `` method. When the
143165 type is a float, you cannot use it to determine a min or max value of the
144166 float (e.g. you want a float to be greater than ``5 ``, ``4.512313 `` is not valid
145- but ``length(4.512314) > length(5) `` is, so the pattern will success ). In
167+ but ``length(4.512314) > length(5) `` is, so the pattern will succeed ). In
146168 this case, the value should be set to ``null `` with a ``MEDIUM_CONFIDENCE ``.
147169
148170Registering a Type Guesser
@@ -164,6 +186,6 @@ The last thing you need to do is registering your custom type guesser by using
164186
165187.. note ::
166188
167- When you use the full stack framework, you need to register your type
168- guesser and tag it with ``form.type_guesser ``. For more information see
189+ When you use the Symfony framework, you need to register your type guesser
190+ and tag it with ``form.type_guesser ``. For more information see
169191 :ref: `the tag reference <reference-dic-type_guesser >`.
0 commit comments