Issues

ZF-11374: Override default translation for Zend_Validator

Description

I'm using Zend_Locale and Zend_Translate in a custom class


class pplib_Locale extends Zend_Locale {
    
    protected $_translate;
    
    public function __construct() {
        $locale = $this->findLocale();
        $auth = Zend_Auth::getInstance();
        if(($user = $auth->getIdentity()) !== null) {
            $locale = $user->getLocale();
        }
        parent::__construct($locale);
        $this->_translate = new Zend_Translate(array(
            'adapter'           =>'gettext', 
            'content'           => APPLICATION_PATH.'/languages/',
            'scan'              => 'directory',
            'locale'            => $locale,
            'clear'             => true,
            'reload'            => true
        ));
        Zend_Registry::set('pplib_Locale', $this);
    }
    
    public function getTranslate() {
        return $this->_translate;
    }
    
}

and initializing the default translater in Bootstrap


class Bootstrap extends Zend_Application_Bootstrap_Bootstrap
{
[..]
    protected function _initLocale() {
        $locale = new pplib_Locale();
        Zend_Form::setDefaultTranslator($locale->getTranslate());
    }
[..]
}

and I want to override the translation for a form validator error message.


class Application_Form_Login extends Zend_Form
{
    public function init() {
[..]
        $password = new Zend_Form_Element_Password('password');
        $password->setLabel($view->translate('PP_PASSWORD'))
            ->setRequired(true)
            ->setAllowEmpty(false)
            ->addFilter('StringTrim')
            ->addValidator('StringLength', false, array(8))
            ->addValidator('Regex', false, array(
                "/[..]/"
            ))
            ->getValidator('Regex')
                ->setDisableTranslator(true)
                ->setMessage($view->translate('PP_PASSWORD_CHARS'), 'regexNotMatch');
        
[..]
    }   
}

this does not work - the validator still uses the default translation. Is this a bug or correct behavior? Is it possible to override a default translation?

Comments

"Does not work" is useless. What did you do? What result did you expect? What result did you get? What is the content of the locale? Was the requested locale detected by Zend_Translate?

and so on... PS: Zend_Locale does NOT TRANSLATE. Using it to translate things is bad behaviour and should really be avoided to prevent method-quirks. PPS: You disabled translation for the validator... why do you expect to get translated content with a disabled translator?

Egesté - what do you mean with ... the validator still uses the default translation? Class' default or something else? In other words, is the output error "'%value%' does not match against pattern '%pattern%'" or something else?

bq. PPS: You disabled translation for the validator... why do you expect to get translated content with a disabled translator?

I think he disabled the translator to prevent possible double translation. However, as said, this issue is pretty much incomplete for me too.

I didn't think I had left any room for ambiguity, did either of you read the source code I posted in the ticket? Can you see that there's source code in this ticket?.. I will try to explain without using code and assume you cannot see the code I posted...

What I'm doing is extending an instance of Zend_Locale and using it as a wrapper for other locale-specific classes, in this case I'm using it for translation. In the future I plan to also use it for timezone, currencies etc. The name of my Zend_Locale wrapper class is pplib_Locale. The pplib_Locale class creates and stores an instance of Zend_Translate with the following params: *adapter = gettext *content = APPLICATION_PATH.'/languages/' *scan = directory *locale = $locale (This is either the default locale, a detected locale, or a user-specified locale) *clear = true *reload = true

Once I have instantiated all the params I want in pplib_Locale, I save it to the registry. Zend_Registry::set('pplib_Locale', $this);

Then, in Bootstrap, I set the defaul translator for Zend_Form to the translator I initialized in pplib_Locale, like so: Zend_Form::setDefaultTranslator($locale->getTranslate()); // $locale is a valid pplib_Locale, created one line above it in bootstrap

In my gettext files, I have created entries for the various default error messages in various Zend_Validate classes. For example: In the Zend_Validate_Regex class, the error message "key" 'regexNotMatch' has been translated to "Invalid input.".

If I stop here, all my translations work. You don't need to know my locale, you don't need to know anything more than if I stop here all my translations work. My problem has nothing to do with getting translations to work.

Moving on to the issue...

There is one specific form for which I would like to OVERRIDE the default translation for a validation error. The form is my login form, the field is my password field, and the validator is the Regex validator, as you may or may not have seen in the source code I posted.

I have tried to set the error message manually via: $element->getValidator('Regex')->setMessage('PP_PASSWORD_CHARS', 'regexNotMatch'). I expected the translated output of a 'regexNotMatch' error for this form>element>validator to then be the translated text for the gettext key 'PP_PASSWORD_CHARS', but it still gives the default 'regexNotMatch' error message "Invalid input."

So I tried to disable the default translator for the validator via: $element->getValidator('Regex')->setDisableTranslator(true)->setMessage($view->translate('PP_PASSWORD_CHARS'), 'regexNotMatch'); I expected the validators default translator to be disabled, and instead use my translate view helper to set the error message manually for the validation error 'regexNotMatch'. This, too, still outputs the default 'regexNotMatch' error message "Invalid input."

My humble guess is that if error message key, like regexNotMatch, is used as a string to be translated it may override the whole translation process in validator. If I may suggest, you should not use those in your language resource files but full message strings. See for example this resource file.


// Snippet from Zend_Validate_Abstract

    protected function _createMessage($messageKey, $value)
    {
        if (!isset($this->_messageTemplates[$messageKey])) {
            return null;
        }

        $message = $this->_messageTemplates[$messageKey];

        if (null !== ($translator = $this->getTranslator())) {
-->         if ($translator->isTranslated($messageKey)) {
                $message = $translator->translate($messageKey);
            } else {
                $message = $translator->translate($message);
            }
        }

        ...

I can not reproduce this behaviour. Therefor closing this issue as not reproduceable.

Please note that also other validators have a "invalid input" message.

Feel free to reopen when you have additional informations. When you have questions on coding problems please ask within the mailing list.