0

How can you ensure that the base fieldtype validation (required etc) and error messages are still applied when validating $value via the validate($value) function??

Validate method in fieldtype class:

public function validate($value)
{
    if(is_array($value) && $value['type'] != '')
    {
        $linkModel = $this->_valuetToModel($value);
        $validated = $linkModel->validate();
        return $validated ? true : $linkModel->getAllErrors();
    }
    return true;
}

Validate method of custom model that the fieldtype populates and returns to the template:

public function validate($attributes = null, $clearErrors = true)
{
    switch($this->type)
    {
        case('email'):
            if( !filter_var($this->value, FILTER_VALIDATE_EMAIL) )
            {
                $this->addError('value', Craft::t('Please enter a valid email address.'));
            }
            break;

        case('tel'):
            $regexp = '/^[0-9+\(\)#\.\s\/ext-]+$/';
            if(!filter_var($this->value, FILTER_VALIDATE_REGEXP, array('options' => array('regexp' => $regexp))))
            {
                $this->addError('value', Craft::t('Please enter a valid telephone.'));
            }
            break;

        case('custom'):
            if(!filter_var($this->value, FILTER_VALIDATE_URL))
            {
                $this->addError('value', Craft::t('Please enter a valid url.'));
            }
            break;

        case('entry'):
            if($this->value == '')
            {
                $this->addError('value', Craft::t('Please select an entry.'));
            }
            break;

        case('asset'):
            if($this->value == '')
            {
                $this->addError('value', Craft::t('Please select an asset.'));
            }
            break;

        case('category'):
            if($this->value == '')
            {
                $this->addError('value', Craft::t('Please select a category.'));
            }
            break;
        // default:
        //     Craft::dd(parent::validate($attributes, null));
        //     $this->addError('value', Craft::t('Please select a sdfasdfsd.'));
        //     break;
    }

    return !$this->hasErrors();
}
1

Completely untested and this whole pattern feels hacky to me, but something like this should work:

From your field type:

public function validate($value)
{
    if(is_array($value) && $value['type'] != '')
    {
        // Validate the field type.
        $errors = parent::validate($value);

        if (!is_array($errors))
        {
            $errors = array();
        }

        $linkModel = $this->_valuetToModel($value);

        // Validate the model.
        $validated = $linkModel->validate();

        return $validated && empty($errors) ? true : array_merge($linkModel->getAllErrors(), $errors);
    }

    return true;
}

From your model:

public function validate($attributes = null, $clearErrors = true)
{
    switch($this->type)
    {
        case('email'):
            if( !filter_var($this->value, FILTER_VALIDATE_EMAIL) )
            {
                $this->addError('value', Craft::t('Please enter a valid email address.'));
            }
            break;

        ....

    }

    return !$this->hasErrors();
}
5
  • The validate() function in the model or the fieldtype class?? Sep 23 '15 at 20:17
  • So you want to validate the fieldtype as well as a model from the field type and return the combined validation results?
    – Brad Bell
    Sep 23 '15 at 21:04
  • Yep that's the requirement here, assuming there's not a better way? Sep 23 '15 at 21:06
  • Thinking about it, might it be better to validate the fieldtype input pre populate model? Seems like an unnecessary step. Sep 23 '15 at 21:08
  • Updated answer.
    – Brad Bell
    Sep 23 '15 at 21:14

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.