8

Respect Validationで複数のカスタム エラー メッセージを表示するにはどうすればよいですか。

複数のバリデータに対して検証したい入力があります。そして、検証ごとにカスタム エラー メッセージが必要です。

これは私が試したものです:

try {
    Respect\Validation\Validator::create()
        ->key('foo',
            v::length(20)->setName('bar')->setTemplate('Custom length message.')
             ->alnum()->setName('baz')->setTemplate('Custom alnum message.')
        )
        ->assert([
            'foo' => 'Hello, world!',
        ]);
} catch (Respect\Validation\Exceptions\ValidationException $exception) {
    $errors = $exception->findMessages([
        'bar',
        'baz',
    ]);
    var_dump($errors);
}

出力は次のとおりです。

array (size=2)
  'bar' => string '' (length=0)
  'baz' => string 'Custom alnum message.' (length=21)

両方のカスタム エラー メッセージが出力されることを期待していました。

理想的には、次のような 1 つの入力に対してメッセージの配列を取得できます。

var_dump($exception->findMessages(['foo']));

私に与えるだろう:

array (size=1)
  'foo' => 
    array (size=2)
      0 => string 'Custom length message.' (length=22)
      1 => string 'Custom alnum message.' (length=21)

この質問はタンブルウィードのようです。

4

1 に答える 1

3

それらをチェーンしてカスタム メッセージを取得することはできません。これは、チェーンの実装により、個々のルールではなく、最後に呼び出したカスタム メッセージが単にルールセットに割り当てられるためです。

これを実証するために、git からクローンを作成し、bin ディレクトリを作成し、この test.php でサンプルを少し変更しました。

<?php
set_include_path(implode(PATH_SEPARATOR, array(
  realpath('../library')
)));

function __autoload($class_name) {
    include $class_name . '.php';
}

use Respect\Validation\Validator as v;

try {
    $chained = Respect\Validation\Validator::create()
        ->key('foo',
            v::length(20)->setName('bar')->setTemplate('Custom length message.')
             ->alnum()->setName('baz')->setTemplate('Custom alnum message.')
        );

    print_r($chained);

    $chained->assert(array(
            'foo' => 'Hello, world!',
        ));

} catch (Respect\Validation\Exceptions\ValidationException $exception) {
    $errors = $exception->findMessages(array(
        'bar',
        'baz',
    ));
    var_dump($errors);
}

the print_r($chained) shows us:

Respect\Validation\Validator Object
(
    [rules:protected] => Array
        (
            [00000000791c0e000000000030f3f15e] => Respect\Validation\Rules\Key Object
                (
                    [mandatory] => 1
                    [reference] => foo
                    [validator] => Respect\Validation\Validator Object
                        (
                            [rules:protected] => Array
                                (
                                    [00000000791c0e030000000030f3f15e] => Respect\Validation\Rules\Length Object
                                        (
                                            [minValue] => 20
                                            [maxValue] =>
                                            [inclusive] => 1
                                            [name:protected] =>
                                            [template:protected] =>
                                        )

                                    [00000000791c0e020000000030f3f15e] => Respect\Validation\Rules\Alnum Object
                                        (
                                            [additionalChars] =>
                                            [stringFormat] => /^(\s|[a-zA-Z0-9])*$/
                                            [name:protected] =>
                                            [template:protected] =>
                                        )

                                )

                            [name:protected] => baz
                            [template:protected] => Custom alnum message.
                        )

                    [name:protected] => foo
                    [template:protected] =>
                )

        )

    [name:protected] =>
    [template:protected] =>
)

ルールセットが最後の名前と最後に渡されたテンプレートを取得し、実際の検証オブジェクトのどちらも名前またはテンプレートを取得していないことに気付くかもしれません。ライブラリには、あなたがやろうとしていることを実際に行う方法がありません。

そこで道を作ることにした。../binディレクトリにこのクラスを作成し、Valditor クラスを拡張しました。

<?php
use Respect\Validation\Validator as v;
class BubbaValidator extends v {

    public function getRuleset($rulename = null){
        if (is_null($rulename)) return $this->rules;
        foreach ($this->rules as $rule){
            if ($rule->getName() == $rulename){
                return $rule;
            }
        }
    }

    public function getValidatorRules($rulesetName, $ruleType=null){
        $ruleset = $this->getRuleset($rulesetName);
        $validators = $ruleset->validator;

        if (is_null($ruleType)){
            return $validators;
        }

        foreach ($validators->rules as $key=>$validator){
            if (get_class($validator) === 'Respect\Validation\Rules\\'.$ruleType){
                $validator->name = "bar";
                $validator->template = "bubba rocks";
                $validators->rules[$key]->name = "bar";
                $validators->rules[$key]->template = "bubba rocks";
                return $validator;
            }
        }
    }

    public function setValidatorRuleName($rulesetName, $ruleType, $name){
        $ruleset = $this->getRuleset($rulesetName);
        $validators = $ruleset->validator;
        foreach ($validators->rules as $key=>$validator){
            if (get_class($validator) === 'Respect\Validation\Rules\\'.$ruleType){
                $validators->rules[$key]->name = $name;
                return $validator;
            }
        }
    }

    public function setValidatorRuleTemplate($rulesetName, $ruleType, $template){
        $ruleset = $this->getRuleset($rulesetName);
        $validators = $ruleset->validator;
        foreach ($validators->rules as $key=>$validator){
            if (get_class($validator) === 'Respect\Validation\Rules\\'.$ruleType){
                $validators->rules[$key]->template = $template;
                return $validator;
            }
        }
    }

}

次に、スクリプトを変更して実行しました

<?php
set_include_path(implode(PATH_SEPARATOR, array(
  realpath('../library'),
  realpath(__DIR__)
)));

function __autoload($class_name) {
    include $class_name . '.php';
}

use BubbaValidator as v;

try {
    $chained = new BubbaValidator();
    $chained->key('foo',
            v::length(20)->setName('bar')->setTemplate('Custom length message.')
             ->alnum()->setName('baz')->setTemplate('Custom alnum message.')
        );

    $chained->setValidatorRuleName('foo', 'Alnum', 'baz');
    $chained->setValidatorRuleTemplate('foo', 'Alnum', 'Bubba\'s Custom Alnum!');
    $chained->setValidatorRuleName('foo', 'Length', 'bar');
    $chained->setValidatorRuleTemplate('foo', 'Length', 'Bubba\'s Custom Length!');

    $chained->assert(array(
            'foo' => 'Hello, world!',
        ));

} catch (Respect\Validation\Exceptions\ValidationException $exception) {
    $errors = $exception->findMessages(array(
        'bar',
        'baz',
    ));
    var_dump($errors);
}

最終的にこの出力を取得するには:

  D:\Users\Bubba\git\Validation\bin>php test.php 
  array(2) {
    ["bar"]=> 
   string(22) "Bubba's Custom Length!" 
    ["baz"]=>   
    string(21) "Custom alnum message." }

それは楽しかった!

于 2013-03-29T19:20:15.200 に答える