2017-09-14 80 views
7

我在用戶使用表單創建「comision」的捆綁工作,並且我試圖檢查用戶是否還有「信用」。所以我創建了一個自定義驗證器,用於查詢過去的評論,並在信用不足時拋出錯誤。Symfony驗證

我的問題是,如果用戶在「日期」字段中提交錯誤格式的日期(即32-13-20122 24:05)Symfony仍會嘗試運行我的自定義驗證,並且我得到各種錯誤(因爲$comision->getDate()null而不是有效的DateTime對象)。

我得到這個錯誤:

clone method called on non-object

我也可以檢查的$comision->getDate()值在我的自定義驗證有效的datetime,但在我看來,它應該是沒有必要的,因爲我加入這個日期屬性中的規則。

這是我的實體(簡化)

/** 
* @MyValidation\TotalHours() 
*/ 
class Comision 
{ 

/** 
* @ORM\Column(type="datetime") 
* @Assert\DateTime() 
* @Assert\NotNull() 
*/ 
protected $date; 


/** 
* @ORM\Column(type="decimal", nullable=false, scale=1) 
* @Assert\NotBlank() 
*/ 
protected $hours; 

... 

我的窗體類...

class NewComisionType extends AbstractType 
{ 
    public function buildForm(FormBuilderInterface $builder, array $options) 
    { 
      $builder 
       ->add('date', DateTimeType::class, array(
       'widget' => 'single_text', 
       'label' => 'Starting date and time', 
       'format' => 'dd/MM/yyyy HH:mm' 
       )) 
       ->add('hours', ChoiceType::class, array(
        'label'=> 'How many hours', 
        'choices' => array(
         '1:00' => 1, 
         '1:30' => 1.5, 
         '2:00' => 2, 
         '2:30' => 2.5, 
         '3:00' => 3 
        ) 
       )) 
... 

而我對自定義的驗證,檢查過去comisions找到,如果用戶仍「信用」

public function validate($comision, Constraint $constraint) 
{ 
$from = clone $comision->getDate(); 
$from->modify('first day of this month'); 

$to = clone $comision->getDate(); 
$to->modify('last day of this month'); 

$credit = $this->em->getRepository("ComisionsBundle:Comision")->comisionsByDate($comision,$from, $to); 

... 
+0

爲什麼不添加日期驗證? https://symfony.com/doc/current/reference/constraints/Date.html或者,也許在你的自定義驗證器 – kunicmarko20

+0

我做了(我編輯我的問題添加它),但它沒有效果。它似乎運行所有驗證規則,即使數據轉換後沒有有效的日期時間。 –

回答

4

一種方法是按照docs中所述對約束進行分組。

這樣,您可以定義兩組限制條件,而只有第一組中的所有限制條件都有效時,第二組纔會生效。

關於您的用例,您可以將您的自定義約束放在與默認約束不同的組中,以確保您具有正確的$ comision DateTime對象。

+0

比我的更好的解決方案不知道這一點。謝謝! – kunicmarko20

2

To do this, you can use the GroupSequence feature. In this case, an object defines a group sequence, which determines the order groups should be validated.

https://symfony.com/doc/current/validation/sequence_provider.html

該解決方案應該是這樣的:

/** 
* @MyValidation\TotalHours(groups={"Strict"}) 
* @Assert\GroupSequence({"Comision", "Strict"}) 
*/ 
class Comision 

以這種方式,將第一驗證所有約束的羣組中Comision(其是相同Default組)。只有該組中的所有約束都有效,第二組Strict纔會被驗證,確保$comision->getDate()將具有DateTime實例。

+0

這個答案與我的不同之處是什麼? – Greg

+0

我很抱歉,在提交我之前沒有閱讀過您的答案。 – yceruto