Changeset 5923


Ignore:
Timestamp:
01/11/12 22:28:05 (4 months ago)
Author:
vain
Message:
  • added form validation, formelement validation and several validators
  • fixed unit-test for validateForm accordingly
Location:
trunk
Files:
5 added
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/core/viewhelper/form/form.core.php

    r5922 r5923  
    731731    public function formHasErrors() 
    732732    { 
    733         return $this->formerror_flag; 
     733        return $this->error; 
    734734    } 
    735735 
     
    11261126     * 
    11271127     * This is the main formular processing loop. 
    1128      * If the form doesn't validate, redisplay it, else present "Success"-Message! 
     1128     * If the form does not validate, then redisplay it, 
     1129     * else present "Success"-Message! 
    11291130     */ 
    11301131    public function processForm() 
    11311132    { 
    11321133        # check if form has been submitted properly 
    1133         if ($this->validateForm() === false) 
     1134        if ($this->validate() === false) 
    11341135        { 
    11351136            # if not, redisplay the form (decorate with errors + render) 
    1136             $this->addValidator($validator); 
    1137             $this->renderFormWithErrors(); 
    1138  
    1139         } 
    1140         else # form was properly filled, display a success web page 
    1141         { 
    1142             # success!! 
    1143             $this->success(); 
    1144         } 
    1145     } 
    1146  
    1147     public function renderFormWithErrors() 
    1148     { 
    1149  
     1137            $this->addDecorator('errors'); 
     1138            $this->render(); 
     1139 
     1140        } 
     1141        else # form was properly filled, display a success web page or a flashmessage 
     1142        { 
     1143            /** 
     1144             * Success - form content valid. 
     1145             * The "noerror" decorator implementation decides, 
     1146             * if a success web page or a flashmessage is used. 
     1147             */ 
     1148            $this->addDecorator('noerror'); 
     1149            $this->render(); 
     1150        } 
    11501151    } 
    11511152 
     
    16251626     * 
    16261627     * The method iterates (loops over) all formelement objects and calls the validation on each object. 
     1628     * In other words: a form is valid, if all formelement are valid. Suprise, suprise. 
    16271629     * 
    16281630     * @return boolean Returns true if form validates, false if validation fails, because errors exist. 
     
    16371639                $this->setErrorState(true); 
    16381640 
    1639                 # and transfer errormessage from formelement to form errormessages stack 
    1640                 $this->addErrormessage($formelement->getError()); 
     1641                # and transfer errormessages from formelement to form errormessages stack 
     1642                #$this->addErrorMessage($formelement->getErrorMessages()); 
    16411643            } 
    16421644        } 
     
    16791681     } 
    16801682 
    1681      public function addErrormessage($errormessage) 
     1683     public function addErrorMessage($errormessage) 
    16821684     { 
    16831685        $this->errormessages[] = $errormessage; 
    16841686     } 
    16851687 
    1686      public function addErrormessages(array $errormessages) 
     1688     public function addErrorMessages(array $errormessages) 
    16871689     { 
    16881690        $this->errormessages = $errormessages; 
  • trunk/core/viewhelper/form/formelement.core.php

    r5922 r5923  
    5050class Clansuite_Formelement implements Clansuite_Formelement_Interface 
    5151{ 
     52    /** 
     53     * @var string 
     54     */ 
    5255    public $name, $id, $type, $class, $size, $disabled, $maxlength, $style, $onclick; 
    5356 
     
    6164     * validators are stored into an array. making multiple validators for one formelement possible. 
    6265     * 
    63      * @var validator 
     66     * @var array 
    6467     */ 
    6568    protected $validators = array(); 
    6669 
    6770    /** 
    68      * error stack array storing the incomming errors from validators. 
    69      * 
    70      * @var formelement_validation_errors 
    71      */ 
    72     protected $validation_errors = array(); 
     71     * The error messages array stores the incomming errors fromelement validators. 
     72     * 
     73     * @var array 
     74     */ 
     75    protected $errormessages = array(); 
    7376 
    7477    /** 
     
    468471     * expect / setRules 
    469472     * 
    470      * set validation rules 
    471      * $rules['input-firstname']  = "required"; 
    472      * $rules['input-email']      = "required, email"; 
    473      */ 
    474     public function expect($rule) 
     473     * set validation rules as string 
     474     * "required, maxlength=20"; 
     475     * "required, email"; 
     476     */ 
     477    public function setRules($rule) 
    475478    { 
    476479        if(false === is_string($rule)) 
     
    483486        foreach($rules as $rule) 
    484487        { 
    485             $this->addValidator($rule); 
     488            $rule = trim($rule); 
     489 
     490            if(false === strpos($rule, '=')) 
     491            { 
     492                # if there is no "=", then there is no value to set 
     493                # rule is then the name of a validator 
     494                $this->addValidator($rule); 
     495            } 
     496            else # ok -> property name to value relationship 
     497            { 
     498                $array = explode('=', $rule); 
     499                $this->addValidator($array[0], array($array[0] => $array[1])); 
     500            } 
    486501        } 
    487502    } 
     
    492507     * Is a shortcut/proxy/convenience method for addValidator() 
    493508     * 
     509     * @param object|string Formelement Validator 
     510     * @param mixed A Validator Property Value. 
    494511     * WATCH OUT! THIS BREAKS THE CHAINING IN REGARD TO THE FORM 
    495512     * @return Clansuite_Formelement_Validator 
    496513     */ 
    497     public function addValidator($validator) 
     514    public function addValidator($validator, $properties = null) 
    498515    { 
    499516        if(false === is_object($validator)) 
    500517        { 
    501  
     518            if($validator === 'required' and false === $this->isRequired()) 
     519            { 
     520                $this->setRequired(); 
     521            } 
     522 
     523            $validator = $this->getValidator($validator); 
     524        } 
     525 
     526        if(isset($properties)) 
     527        { 
     528            $validator->setProperties($properties); 
    502529        } 
    503530 
    504531        $this->setValidator($validator); 
    505532 
    506         return $this; 
     533        return $validator; 
    507534    } 
    508535 
     
    523550 
    524551    /** 
    525      * The validation method processes all registered validators of a sinngle formelement. 
     552     * Returns a form validator object. 
     553     * Also a factory method, which instantiates and returns a new formvalidator object. 
     554     * 
     555     * @return Clansuite_Formvalidator 
     556     */ 
     557    public function getValidator($validator) 
     558    { 
     559        # load baseclass 
     560        # @todo move to map / autoloader 
     561        if(false == class_exists('Clansuite_Formelement_Validator', false)) 
     562        { 
     563            include ROOT_CORE . 'viewhelper/form/validator.php'; 
     564        } 
     565 
     566        # construct classname 
     567        $class = 'Clansuite_Formelement_Validator_' . ucfirst($validator); 
     568 
     569        # return early, if this object is already stored 
     570        if(isset($this->validators[$class])) 
     571        { 
     572            return $this->validators[$class]; 
     573        } 
     574        # autoloader 
     575        elseif(true === class_exists($class)) 
     576        { 
     577 
     578            return new $class; 
     579        } 
     580        # factory method part 
     581        elseif(false == class_exists($class, false)) 
     582        { 
     583            $file = ROOT_CORE . 'viewhelper/form/validators/' . $validator . '.php'; 
     584 
     585            if(is_file($file) === true) 
     586            { 
     587                include $file; 
     588            } 
     589            unset($file); 
     590 
     591            return new $class(); 
     592        } 
     593        # validator not found 
     594        else 
     595        { 
     596            throw new Clansuite_Exception('Validator named ' . $validator . ' not available.'); 
     597        } 
     598    } 
     599 
     600    /** 
     601     * Validates the value of a formelement. 
     602     * 
     603     * The validation method processes the value of the formelement 
     604     * by passing it to all registered validators of the formelement. 
     605     * The value of the formelement is valid, when it satisfies 
     606     * each of the element's validation rules. 
    526607     * 
    527608     * @see $validators array 
     
    530611    public function validate() 
    531612    { 
     613        $value = $this->getValue(); 
     614 
     615        # return early, if value empty|null and not required 
     616        if((('' === $value) or (null === $value)) and false === $this->isRequired()) 
     617        { 
     618            return true; 
     619        } 
     620 
     621        # no rules / validators 
     622        if(null === $this->validators) 
     623        { 
     624            return true; 
     625        } 
     626 
    532627        # iterate over all validators 
    533628        foreach($this->validators as $validator) 
    534629        { 
    535630            # ensure element validates 
    536             if($validator->validates() === true) 
     631            if($validator->validate($value) === true) 
    537632            { 
    538633                # everything is fine, proceed 
     
    545640 
    546641                # and transfer error message from the validator to the formelement 
    547                 $this->addError($validator->getError()); 
     642                $this->addErrorMessage($validator->getErrorMessage()); 
    548643 
    549644                return false; 
    550645            } 
    551646        } 
     647 
     648        # formelement value is valid 
     649        return true; 
    552650    } 
    553651 
     
    555653     * Method adds an validation error to the formelement_validation_error stack. 
    556654     * 
     655     * @param $errormessage 
     656     */ 
     657    public function addErrorMessage($errormessage) 
     658    { 
     659        $this->errormessages[] = $errormessage; 
     660    } 
     661 
     662    /** 
     663     * Returns the validation_error stack. 
     664     * 
    557665     * @param $validation_error 
    558666     */ 
    559     public function addError($validation_error) 
    560     { 
    561         $this->validation_errors[] = $validation_error; 
     667    public function getErrorMessages() 
     668    { 
     669        return $this->errormessages; 
    562670    } 
    563671 
     
    606714    public function __toString() 
    607715    { 
    608         #var_dump(get_class($this)); 
    609716        $subclass = get_class($this); 
    610717 
     
    735842     * Factory method. Instantiates and returns a new formdecorator object. 
    736843     * 
     844     * @param string Formelement Decorator. 
    737845     * @return Clansuite_Formelement_Decorator 
    738846     */ 
    739     public function decoratorFactory($formelementdecorator) 
     847    public function decoratorFactory($decorator) 
    740848    { 
    741849        # construct Clansuite_Formdecorator_Name 
    742         $formelementdecorator_classname = 'Clansuite_Formelement_Decorator_' . ucfirst($formelementdecorator); 
     850        $class = 'Clansuite_Formelement_Decorator_' . ucfirst($decorator); 
    743851 
    744852        # if not already loaded, require forelement file 
    745         if(false == class_exists($formelementdecorator_classname, false)) 
    746         { 
    747             $file = ROOT_CORE . 'viewhelper/form/formdecorators/formelement/' . $formelementdecorator . '.form.php'; 
     853        if(false == class_exists($class, false)) 
     854        { 
     855            $file = ROOT_CORE . 'viewhelper/form/formdecorators/formelement/' . $decorator . '.form.php'; 
    748856 
    749857            if(is_file($file) === true) 
     
    754862 
    755863        # instantiate the new $formdecorator 
    756         return new $formelementdecorator_classname; 
     864        return new $class; 
    757865    } 
    758866 
  • trunk/tests/unittests/core/viewhelper/form/form.core.php

    r5922 r5923  
    728728    }*/ 
    729729 
    730     public function testValidateForm() 
    731     { 
    732         $this->form->addElement('textarea')->setRequired()->expect('required, string, maxlength=100'); 
    733  
    734  
    735         $this->form->validateForm(); 
    736  
    737         // Remove the following lines when you implement this test. 
    738         $this->markTestIncomplete( 
    739                 'This test has not been implemented yet.' 
    740         ); 
     730    public function testValidateForm_false() 
     731    { 
     732        $this->form->addElement('textarea') 
     733                ->setName('Textarea-Validate-Test') 
     734                ->setRequired() 
     735                ->setRules('required, string, maxlength=100'); 
     736 
     737        # no value set, but required 
     738        $this->assertFalse($this->form->validateForm()); 
     739 
     740        # set a value, exceeding maxlength 
     741        $element = $this->form->getElementByName('Textarea-Validate-Test'); 
     742        $element->setValue('0123456789-0123456789'); # 21 chars 
     743 
     744        # max length exceeded 
     745        $this->assertFalse($this->form->validateForm()); 
     746    } 
     747 
     748    public function testValidateForm_true() 
     749    { 
     750        $this->form->addElement('textarea') 
     751                ->setName('Textarea-Validate-Test') 
     752                ->setRequired() 
     753                ->setRules('required, string, maxlength=20'); 
     754 
     755        # set value, length ok 
     756        $element = $this->form->getElementByName('Textarea-Validate-Test'); 
     757        $element->setValue('01234567890123456789'); # 20 chars 
     758 
     759        $this->assertTrue($this->form->validateForm()); 
    741760    } 
    742761 
Note: See TracChangeset for help on using the changeset viewer.