我在Symfony 2中构建了一个自定义约束验证,它调用了Doctrine:
if($prevu != 0) {
$total = $prevu + $consomme;
if($total > $charge) {
$this->context->buildViolation($constraint->message1)
->setParameter('%string%', $prevu)
->atPath('intervention.dureeP')
->addViolation();
}
dump($this);
}elseif($realise != 0) {
$total = $realise + $consomme;
if($total > $charge) {
$this->context->buildViolation($constraint->message2)
->setParameter('%string%', $realise)
->atPath('dureeR')
->addViolation();
}
}
我的问题是错误不会显示在字段旁边,而是显示在表单的顶部。
我用这样的注释调用我的自定义验证器:
/**
* @var string
*
* @ORM\Column(name="duree_p", type="decimal", precision=3, scale=2, nullable=true)
* @MyAssert\ExceedCharge
*/
private $dureeP;
奇怪的是,形成一些字段,它会在旁边显示错误,但对于其他字段,它会在顶部显示错误。
我在StackOverflow上看过这篇文章:Custom constraint validation error doesn't display next to field in Symfony2但它对我没有帮助。
我尝试了选项“atPath()”但没有成功。
我不明白的是,它适用于某些领域而不适合我想要的领域......
有人有任何线索吗?
编辑:
我还注意到,当违规消息发生时,与违规消息相关的字段没有任何“has-error”类,因此没有“。
编辑2:
这是我的约束逻辑:
class ExceedChargeValidator extends ConstraintValidator
{
protected $em;
public function __construct(EntityManager $em)
{
$this->em = $em;
}
public function validate($value, Constraint $constraint)
{
dump($value); //DEBUG
dump($this->context); //DEBUG
//get id to perform search
$id = $this->context->getObject()->getCast()->getId();
$consomme = $this->em->getRepository('AppBundle:Intervention')->getConsomme($id);
$charge = $this->context->getObject()->getCast()->getCharge();
$prevu = $this->context->getObject()->getDureeP();
$realise = $this->context->getObject()->getDureeR();
dump($prevu); //DEBUG
dump($realise); //DEBUG
if($value != 0) {
$total = $value + $consomme;
if($total > $charge) {
$this->context->buildViolation($constraint->message1)
->setParameter('%string%', $value)
->addViolation();
dump($this->context->getPropertyPath());
}
dump($this); //DEBUG
}
dump($consomme);//DEBUG
dump($charge); //DEBUG
}
}
以下是我的实体的一些诅咒:
/**
* @var \DateTime
*
* @ORM\Column(name="date", type="date")
*/
private $date;
/**
* @var string
*
* @ORM\Column(name="duree_p", type="decimal", precision=3, scale=2, nullable=true)
* @MyAssert\ExceedCharge
*/
private $dureeP;
/**
* @var string
*
* @ORM\Column(name="duree_r", type="decimal", precision=3, scale=2, nullable=true)
* @Assert\GreaterThan(
* value = 0
*)
*/
private $dureeR;
表单由Easy Admin软件包生成
如果我将相同的约束违规附加到不同的字段,这是我得到的。我们可以看到它在我的“日期”字段中正常工作,但对于“dureeP”字段,消息显示在顶部
答案 0 :(得分:0)
你的atPath
似乎没用,因为你的Constraint是一个应用于字符串的PropertyConstraint,而字符串没有子节点。
但是,当属性约束引发违规时,违规将附加到具有属性名称(如果存在)的字段。因此,如果您的表单中包含dureeP
字段,则会将错误附加到该字段,否则它将位于表单的根目录。
答案 1 :(得分:0)
好的,我发现了问题!
问题出在我的专栏名称上,包括" _" (下划线)。
我替换了
@ORM\Column(name="duree_p", type="decimal", precision=3, scale=2)
通过
@ORM\Column(name="prevu", type="decimal", precision=3, scale=2)
它解决了这个问题。因此,名称中没有下划线,我们已经完成了!
我是怎么找到的? 通过创建虚拟(基本)验证器测试并将其附加到我的另一个实体的某些字段。我看到它正在所有领域工作,所以我比较了两个实体之间的差异,这是唯一的区别。
以下是我用于排除故障的验证程序:
class TestValidator extends ConstraintValidator
{
protected $em;
public function __construct(EntityManager $em)
{
$this->em = $em;
}
public function validate($value, Constraint $constraint)
{
dump($value);
if(!preg_match('/^[0-9]+$/', $value, $matches)) {
$this->context->buildViolation($constraint->message)
->setParameter('%string%', $value)
->addViolation();
}
}
}