O ZendFramework possui muitos validators prontos, porém algumas vezes é necessário criar alguns específicos, como por exemplo a validação de CPF, que por padrão não tem no Framework. Mas e como fazer isso? Descreverei a seguir:
Primeiro vamos criar o Validate no caminho lybrary/My/Validate/Cpf.php
<?php /** * @see Zend_Validate_Abstract */ require_once 'Zend/Validate/Abstract.php'; class My_Validate_Cpf extends Zend_Validate_Abstract { const NOT_CPF = 'notCpf'; protected $_messageTemplates = array( self::NOT_CPF => "'%value%' não é um CPF válido.", ); protected $_numericOnly; /** * Se o CPF for apenas numerico 12345678909 então $numbersOnly é true * Se não, 123.456.789-09 * @param bool $numbersOnly */ public function __construct($numbersOnly = false) { $this->_setNumericOnly($numbersOnly); } /** * Sets $_numericOnly * @param bool $bool */ private function _setNumericOnly($bool = false){ $this->_numericOnly = $bool; if($this->_numericOnly === true){ $this->_regexp = '/^(d){11}$/'; } else{ $this->_regexp = '/^(d){3}(.d{3}){2}-(d){2}$/'; } return $this; } /** * * @param mixed $value * @return boolean * @throws Zend_Valid_Exception If validation of $value is impossible * @see Zend_Validate_Interface::isValid() */ public function isValid($value) { // checks regexp, first and second validation Digit if ( preg_match($this->_regexp, $value) && $this->_checkDigitOne($this->_removeNonDigits($value)) && $this->_checkDigitTwo($this->_removeNonDigits($value)) ){ return true; } $this->_setValue($value); $this->_error(self::NOT_CPF); return false; } /** * * @param string $value * @return bool */ private function _checkDigitOne($value) { $multipliers = array(10,9,8,7,6,5,4,3,2); return $this->_getDigit($value, $multipliers) == $value{9}; } /** * * @param string $value * @return bool */ private function _checkDigitTwo($value) { $multipliers = array(11,10,9,8,7,6,5,4,3,2); return $this->_getDigit($value, $multipliers) == $value{10}; } /** * * @param string $value * @param array(int) $multipliers * @return int */ private function _getDigit($value, $multipliers) { foreach($multipliers as $key => $v){ $sum += $value{$key} * $v; } $digit = $sum % 11; if ($digit < 2) { $digit = 0; }else{ $digit = 11 - $digit; } return $digit; } /** * * @param string $value * @return string */ private function _removeNonDigits($value) { return preg_replace('/D/', '', $value); } } ?>
O validate já está criado e a forma de usa-lo é bem semelhante aos demais validators, vamos então criar o formulário no caminho: application/forms/ValidaCpf.php.
<?php class Application_Form_ValidaCpf extends Zend_Form { public function init() { Zend_Dojo::enableForm($this); } public function __construct($options = null) { parent::__construct ($options); //definicoes do campo CPF //$cpf = new Zend_Form_Element_Text('cpf'); $cpf = new Zend_Dojo_Form_Element_TextBox('cpf'); $cpf->setLabel('CPF: ') ->setTrim(true) ->setRequired(true) ->addFilter('Alnum') ->addFilter('StripTags') ->addFilter('StringTrim') ->addValidator('NotEmpty', true, array('messages' => array('isEmpty' => 'Preencha este campo antes de prosseguir!'))) ->addPrefixPath('My_Validate', 'My/Validate/', 'validate') ->addValidator('Cpf', true, array(true)); //definicoes do botao de enviar $enviar = new Zend_Dojo_Form_Element_SubmitButton('enviar'); $enviar->setLabel('Enviar'); $this->addElements(array($cpf, $enviar)); } } ?>
Instancie o Form onde ele será utilizado e pronto, no caso aqui para exemplo será utilizado no IndexController.php na action validaCpf no caminho: application/controllers/IndexController.php
<?php class IndexController extends Zend_Controller_Action { public function init() { Zend_Dojo::enableView($this->view); } public function indexAction() { // action body } public function validaCpfAction() { $form = new Application_Form_ValidaCpf(array( 'action' => $this->view->baseUrl().'/index/valida-cpf', 'method' => 'post')); $this->view->form = $form; //se o formulario foi enviado via post if ($this->getRequest()->isPost()) { //recupera os dados enviados $formData = $this->getRequest()->getPost(); //se o formulario foi preenchido corretamente if ($form->isValid($formData)) { echo 'valido'; }else { //popula os campos com os dados preenchidos $form->populate($formData); } } } ?>
e por fim a view no caminho: application/views/scripts/index/valida-cpf.phtml
Validação de CPF <?php echo $this->form;