Symfony2:在验证器中访问原始表单数据

时间:2016-08-08 06:56:53

标签: php forms validation symfony

我为Symfony2表单创建了自己的验证器。它被称为ValidDateValidator,它应该过滤掉无效日期,例如2015-02-31。表单类型如下所示:

->add(
        'thedate',
        DateType::class,
        array(
            'widget' => 'single_text',
            'format' => 'yyyy-MM-dd',
            'constraints' => array(
                new ValidDate()
            )
        )
)

现在如果我尝试在我的验证器中访问这个:

public function validate($value, Constraint $constraint){
    //this returns 2015-03-03 
    echo $value->format('Y-m-d'); 
}

结果我得到“2015-03-03”。有没有办法在不处理原始表单数据的情况下访问它们?

2 个答案:

答案 0 :(得分:2)

不幸的是,这是不可能的。验证者在data transformation之后收到他们的数据。

您可以做的是创建自己的视图转换器并使用它而不是标准转换器。视图转换器获取输入数据并将其转换为标准数据。在DateField的情况下,这只是DateTime-Object。

您可以在此转换期间抛出异常,这会导致表单错误。更具体地说,它会显示invalid_message中的DateField

让我试着举个例子:

变压器:

namespace AppBundle\Form\DataTransformer;

use Doctrine\Common\Persistence\ObjectManager;
use Symfony\Component\Form\DataTransformerInterface;
use Symfony\Component\Form\Exception\TransformationFailedException;

class StringToDateTransformer implements DataTransformerInterface
{  
    /**
     * Transforms a DateTime object to a string .
     *
     * @param  DateTime|null $date
     * @return string
     */
    public function transform($date)
    {
        if (null === $date) {
            return '';
        }

        return $date->format('Y-m-d');
    }

    /**
     * Transforms a string to a DateTime object.
     *
     * @param  string $dateString
     * @return DateTime|null
     * @throws TransformationFailedException if invalid format/date.
     */
    public function reverseTransform($dateString)
    {
        //Here do what ever you would like to do to transform the string to 
        //a DateType object
        //The important thing is to throw an TransformationFailedException
        //if something goes wrong (such as wrong format, or invalid date):

        throw new TransformationFailedException('The date is incorrect!');

        return $dateTime;
    }
}

在您的表单构建器中:

$builder->get('thedate')
            //Important!
            ->resetViewTransformers()
            ->addViewTransformer(new StringToDateTransformer());

请注意resetViewTransformers()来电。某些字段(如DateType)已有视图转换器。通过调用此方法,我们摆脱了这个默认变换器,导致只调用我们的transfomrer。

答案 1 :(得分:1)

其\ DateTime :: format将额外天数转换为新日期。不是来自表单的数据。

您可以使用checkdate查看您是否拥有此类有效组件。

$dateString = '2015-2-31';

$bits = explode('-', $dateString); // split the string
list($y, $m, $d) = $bits; // variablise the parts

if(checkdate($m, $d, $y)) {
    // do something
} else {
    // do something else
}

example