Zend_Validate-WritingValidators.xml 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273
  1. <?xml version="1.0" encoding="UTF-8"?>
  2. <!-- EN-Revision: 24249 -->
  3. <!-- Reviewed: no -->
  4. <sect1 id="zend.validate.writing_validators">
  5. <title>Écrire des validateurs</title>
  6. <para>
  7. <classname>Zend_Validate</classname> fournit un ensemble de validateurs habituellement
  8. nécessaires, mais inévitablement, les développeurs souhaiteront écrire des validateurs sur
  9. mesure pour leurs besoins particuliers. La méthode d'écriture d'un validateur personnalisé
  10. est décrit dans cette section.
  11. </para>
  12. <para>
  13. <classname>Zend_Validate_Interface</classname> définit trois méthodes,
  14. <methodname>isValid()</methodname>, <methodname>getMessages()</methodname>, et <methodname>getErrors()</methodname>, qui peuvent
  15. être implémentées par des classes d'utilisateur afin de créer les objets de validation sur
  16. mesure. Un objet qui implémente l'interface <classname>Zend_Validate_Interface</classname>
  17. peut être ajouté à une chaîne de validateur avec
  18. <methodname>Zend_Validate::addValidator()</methodname>. De tels objets peuvent également être
  19. employés avec <link
  20. linkend="zend.filter.input"><classname>Zend_Filter_Input</classname></link>.
  21. </para>
  22. <para>
  23. Comme vous avez déjà pu déduire de la description ci-dessus de
  24. <classname>Zend_Validate_Interface</classname>, les classes de validation fournie avec Zend
  25. Framework retourne une valeur booléenne pour savoir si une valeur est validée ou non. Elles
  26. fournissent également des informations sur la raison pour laquelle la validation a échoué
  27. sur une valeur. La mise à disposition de ces raisons d'échec de validation peut être
  28. utilisée par une application dans différents buts, tels que fournir des statistiques pour
  29. l'analyse de la facilité d'utilisation.
  30. </para>
  31. <para>
  32. La fonctionnalité de base de message d'échec de validation est implémentée dans
  33. <classname>Zend_Validate_Abstract</classname>. Pour inclure cette fonctionnalité en créant
  34. une classe de validation, étendez simplement <classname>Zend_Validate_Abstract</classname>.
  35. Dans la classe étendue vous implémenteriez la logique de la méthode <methodname>isValid()</methodname>
  36. et définiriez les variables de message et les modèles de message qui correspondent aux types
  37. d'échecs de validation qui peuvent se produire. Si une valeur ne passe pas vos essais de
  38. validation, alors <methodname>isValid()</methodname> devrait renvoyer <constant>FALSE</constant>. Si la valeur
  39. passe vos essais de validation, alors <methodname>isValid()</methodname> devrait renvoyer
  40. <constant>TRUE</constant>.
  41. </para>
  42. <para>
  43. En général, la méthode <methodname>isValid()</methodname> ne devrait lever aucune exception,
  44. excepté où il est impossible de déterminer si la valeur d'entrée est valide. Quelques
  45. exemples de cas raisonnables pour lever une exception pourraient être si un fichier ne peut
  46. pas être ouvert, un serveur de <acronym>LDAP</acronym> ne pourraient pas être contacté, ou une connexion de
  47. base de données est indisponible, où quand une telle chose peut être exigée pour que le
  48. succès ou l'échec de validation soit déterminé.
  49. </para>
  50. <example id="zend.validate.writing_validators.example.simple">
  51. <title>Création d'une simple classe de validation</title>
  52. <para>
  53. L'exemple suivant démontre comment un validateur personnalisé très simple pourrait
  54. être écrit. Dans ce cas-ci les règles de validation sont simplement que la valeur
  55. d'entrée doit être une valeur en virgule flottante. <programlisting language="php"><![CDATA[
  56. class MonValidateur_Float extends Zend_Validate_Abstract
  57. {
  58. const FLOAT = 'float';
  59. protected $_messageTemplates = array(
  60. self::FLOAT => "'%value%' n'est pas une valeur en virgule flottante"
  61. );
  62. public function isValid($value)
  63. {
  64. $this->_setValue($value);
  65. if (!is_float($value)) {
  66. $this->_error();
  67. return false;
  68. }
  69. return true;
  70. }
  71. }
  72. ]]></programlisting> La classe définit un modèle pour son message unique d'échec de validation,
  73. qui inclut le paramètre magique intégré, <code>%value%</code>. L'appel à
  74. <methodname>_setValue()</methodname> prépare l'objet pour insérer automatiquement la valeur examinée
  75. dans le message d'échec, si la validation de la valeur échoue. L'appel à
  76. <methodname>_error()</methodname> trace la raison d'échec de validation. Puisque cette classe
  77. définit seulement un message d'échec, il n'est pas nécessaire de fournir à
  78. <methodname>_error()</methodname> le nom du modèle de message d'échec.
  79. </para>
  80. </example>
  81. <example id="zend.validate.writing_validators.example.conditions.dependent">
  82. <title>Écriture d'une classe de validation ayant des conditions de dépendances</title>
  83. <para>
  84. L'exemple suivant démontre un ensemble plus complexe de règles de validation, où
  85. on l'exige que la valeur d'entrée doit être numérique et dans la plage des valeurs
  86. limites minimum et maximum. Une valeur d'entrée ferait échouer la validation pour
  87. exactement une des raisons suivantes : <itemizedlist>
  88. <listitem>
  89. <para>La valeur d'entrée n'est pas numérique.</para>
  90. </listitem>
  91. <listitem>
  92. <para>
  93. La valeur d'entrée est inférieure que la valeur permise
  94. minimum.
  95. </para>
  96. </listitem>
  97. <listitem>
  98. <para>
  99. La valeur d'entrée est supérieure que la valeur permise
  100. maximum.
  101. </para>
  102. </listitem>
  103. </itemizedlist>
  104. </para>
  105. <para>
  106. Ces raisons d'échec de validation sont alors traduites dans les définitions de la
  107. classe : <programlisting language="php"><![CDATA[
  108. class MonValidateur_NumericBetween extends Zend_Validate_Abstract
  109. {
  110. const MSG_NUMERIC = 'msgNumeric';
  111. const MSG_MINIMUM = 'msgMinimum';
  112. const MSG_MAXIMUM = 'msgMaximum';
  113. public $minimum = 0;
  114. public $maximum = 100;
  115. protected $_messageVariables = array(
  116. 'min' => 'minimum',
  117. 'max' => 'maximum'
  118. );
  119. protected $_messageTemplates = array(
  120. self::MSG_NUMERIC => "'%value%' n'est pas numérique",
  121. self::MSG_MINIMUM => "'%value%' doit être supérieure à '%min%'",
  122. self::MSG_MAXIMUM => "'%value%' doit être inférieure à '%max%'"
  123. );
  124. public function isValid($value)
  125. {
  126. $this->_setValue($value);
  127. if (!is_numeric($value)) {
  128. $this->_error(self::MSG_NUMERIC);
  129. return false;
  130. }
  131. if ($value < $this->minimum) {
  132. $this->_error(self::MSG_MINIMUM);
  133. return false;
  134. }
  135. if ($value > $this->maximum) {
  136. $this->_error(self::MSG_MAXIMUM);
  137. return false;
  138. }
  139. return true;
  140. }
  141. }
  142. ]]></programlisting> Les propriétés publiques <varname>$minimum</varname> et <varname>$maximum</varname> ont
  143. été établies pour fournir les frontières minimum et maximum d'une valeur pour qu'elle
  144. soit validée avec succès. La classe définit également deux variables de message qui
  145. correspondent aux propriétés publiques et permettent que <code>min</code> et
  146. <code>max</code> soient employés dans des modèles de message en tant que paramètres
  147. magiques, comme avec <code>value</code>.
  148. </para>
  149. <para>
  150. Noter que si n'importe quel élément de la validation vérifié dans
  151. <methodname>isValid()</methodname> échoue, un message approprié d'échec est préparé, et la méthode
  152. renvoie immédiatement <constant>FALSE</constant>. Ces règles de validation sont donc
  153. séquentiellement dépendantes. C'est-à-dire, que si un essai échoue, il n'y a aucun
  154. besoin d'examiner les règles suivantes de validation. Ce besoin peut exister, cependant.
  155. L'exemple suivant illustre comment écrire une classe ayant des règles indépendantes de
  156. validation, où l'objet de validation peut renvoyer des raisons multiples pour lesquelles
  157. une tentative particulière de validation a échoué.
  158. </para>
  159. </example>
  160. <example id="zend.validate.writing_validators.example.conditions.independent">
  161. <title>Validation avec des conditions indépendantes, avec raisons multiples
  162. d'échec</title>
  163. <para>
  164. Considérons l'écriture d'une classe de validation pour le contrôle de résistance
  165. d'un mot de passe - quand un utilisateur est requis afin de choisir un mot de passe qui
  166. respecte certains critères pour aider à la sécurisation des comptes d'utilisateur.
  167. Supposons que les critères de sécurité de mot de passe imposent que le mot de passe :
  168. <itemizedlist>
  169. <listitem>
  170. <para>est au moins une longueur de 8 caractères,</para>
  171. </listitem>
  172. <listitem>
  173. <para>contient au moins une lettre majuscule,</para>
  174. </listitem>
  175. <listitem>
  176. <para>contient au moins une lettre minuscule,</para>
  177. </listitem>
  178. <listitem>
  179. <para>et contient au moins un caractère de chiffre.</para>
  180. </listitem>
  181. </itemizedlist>
  182. </para>
  183. <para>
  184. La classe suivante implémente ces critères de validation : <programlisting
  185. role="php"><![CDATA[
  186. class MonValidateur_PasswordStrength extends Zend_Validate_Abstract
  187. {
  188. const LENGTH = 'length';
  189. const UPPER = 'upper';
  190. const LOWER = 'lower';
  191. const DIGIT = 'digit';
  192. protected $_messageTemplates = array(
  193. self::LENGTH =>
  194. "'%value%' doit avoir une longueur d'au moins 8 caractères",
  195. self::UPPER =>
  196. "'%value%' doit contenir au moins une lettre majuscule",
  197. self::LOWER =>
  198. "'%value%' doit contenir au moins une lettre minuscule",
  199. self::DIGIT =>
  200. "'%value%' doit contenir au moins un chiffre"
  201. );
  202. public function isValid($value)
  203. {
  204. $this->_setValue($value);
  205. $isValid = true;
  206. if (strlen($value) < 8) {
  207. $this->_error(self::LENGTH);
  208. $isValid = false;
  209. }
  210. if (!preg_match('/[A-Z]/', $value)) {
  211. $this->_error(self::UPPER);
  212. $isValid = false;
  213. }
  214. if (!preg_match('/[a-z]/', $value)) {
  215. $this->_error(self::LOWER);
  216. $isValid = false;
  217. }
  218. if (!preg_match('/\d/', $value)) {
  219. $this->_error(self::DIGIT);
  220. $isValid = false;
  221. }
  222. return $isValid;
  223. }
  224. }
  225. ]]></programlisting>Noter que les quatre critères d'essais dans <methodname>isValid()</methodname> ne
  226. renvoient pas immédiatement <constant>FALSE</constant>. Ceci permet à la classe de validation de
  227. fournir toutes les raisons pour lesquelles le mot de passe d'entrée n'a pas réussi à
  228. remplir les conditions de validation. Si, par exemple, un utilisateur entre la chaîne
  229. "<code>#$%</code>" comme mot de passe, <methodname>isValid()</methodname> entraînera que les quatre
  230. messages d'échec de validation seront retournés lors de l'appel suivant à
  231. <methodname>getMessages()</methodname>.
  232. </para>
  233. </example>
  234. </sect1>