2017-10-18 150 views
0

我目前正在开发一个Symfony v3.3.6项目。 我有一个用于创建用户的表单。 我想确保电子邮件和用户名(fos用户包)是唯一的。Symfony - 唯一的实体约束不起作用

我目前拥有这个模型(仅一小部分):

<?php 

namespace ProjectBundle\Entity\User; 

use Doctrine\ORM\Mapping as ORM; 
use FOS\UserBundle\Model\User as BaseUser; 
use Gedmo\Mapping\Annotation as Gedmo; 
use Gedmo\SoftDeleteable\Traits\SoftDeleteableEntity; 
use Gedmo\Timestampable\Traits\TimestampableEntity; 
use ProjectBundle\Entity\Gender\Gender; 
use ProjectBundle\Entity\Organisation\Organisation; 
use ProjectBundle\Entity\Traits\BlameableEntity; 
use ProjectBundle\Entity\User\Profile; 
use Symfony\Component\Security\Core\User\AdvancedUserInterface; 
use Symfony\Component\Validator\Constraints as Assert; 
use Symfony\Component\Validator\Context\ExecutionContextInterface; 
use Doctrine\Common\Collections\ArrayCollection; 
use Symfony\Bridge\Doctrine\Validator\Constraints\UniqueEntity; 
use Symfony\Bridge\Doctrine\Validator\Constraints\UniqueEntityValidator; 


/** 
* @ORM\Entity(repositoryClass="ProjectBundle\Repository\User\UserRepository") 
* @Gedmo\SoftDeleteable(fieldName="deletedAt") 
* @ORM\Entity 
* @UniqueEntity(fields={"email"}, groups={"registration"}) 
* @UniqueEntity(fields={"username"}, groups={"registration"}) 
* @ORM\Table(name="user") 
*/ 
class User extends BaseUser implements AdvancedUserInterface, \Serializable 
{ 
    use TimestampableEntity; 
    use SoftDeleteableEntity; 
    use BlameableEntity; 

    const ID_ORGA_GC = 1; 

    /** 
    * @var int 
    * 
    * @ORM\Column(name="id", type="integer") 
    * @ORM\Id 
    * @ORM\GeneratedValue(strategy="AUTO") 
    */ 
    protected $id; 


    /** 
    * @Assert\NotBlank() 
    */ 
    protected $username; 

    /** 
    * @Assert\NotBlank(groups={"registration"}) 
    * @Assert\Length(groups={"registration"}, 
    *  min = 2, 
    *  max = 254, 
    *  minMessage = "Votre mot de passe doit comporter au minimum {{ limit }} caractères.", 
    *  maxMessage = "Votre mot de passe doit comporter au maximum {{ limit }} caractères." 
    *) 
    * 
    * @var string 
    */ 
    protected $plainPassword; 


    /** 
    * @Assert\NotBlank() 
    * @Assert\Email(
    *  message = "L'adresse mail '{{ value }}' n'est pas valide.", 
    *  checkMX = true 
    *) 
    * 
    * @var string 
    */ 
    protected $email; 

正如你可以看到我加2“唯一的实体”属性,输入用户名和电子邮件,还与每一个“NotBlank”约束。

在我的控制,我打电话给我的表格:

$form = $this->createForm('ProjectBundle\Form\User\UserType', $entity,array('organisation' => $organisations, 'validation_groups' => array('Default','registration'))); 

$form->handleRequest($request); 

     if ($form->isSubmitted()) { 
      if ($form->isValid()) { 

然而,即使我写的已经存在的E-mail地址,我进入状态,并在时机成熟时进行冲洗我得到一个大的SQL错误:

SQLSTATE [23000]: Integrity constraint violation: 1062 Duplicate entry '[email protected]' for key 'UNIQ_8D93D649A0D96FBF' 

但有趣的一句话是,“NotBlank”约束正常工作,并显示出我的我的看法“的值不能为空”

这里我的表单:

class UserType extends AbstractType 
{ 
    /** 
    * {@inheritdoc} 
    */ 
    public function buildForm(FormBuilderInterface $builder, array $options) 
    { 
     $builder->add('lastname',null,array('required' => true)) 
      ->add('firstname') 
      ->add('gender',null,array('required'=>true)) 
      ->add('organisationMember',null,array(
       'required' => true, 
       'choices' => $options['organisation'], 
       'group_by' => 'type_organisation', 
       'placeholder' => 'Choisissez votre organisation' 
      )) 
      ->add('job') 
      ->add('lang', null, array(
       'required' => true 
      )) 
      ->add('mobile',null, array(
       'required' => false 
      )) 
      ->add('phone', null, array(
       'required' => true 
      )) 
      ->add('enabled') 
      ->add('is_external') 
      ->add('alert_failure') 
      ->add('alert_full') 
      ->add('alert_other') 
      ->add('plainPassword', TextType::class, array('required' => false)) 
      ->add('email') 
      ->add('profile', null, array(
       'required' => true, 
       'placeholder' => 'Choose an organisation !', 
      )); 
    } 

    /** 
    * {@inheritdoc} 
    */ 
    public function configureOptions(OptionsResolver $resolver) 
    { 
     $resolver->setDefaults(array(
      'data_class' => 'ProjectBundle\Entity\User\User', 
      'organisation' => 'ProjectBundle\Entity\Organisation\Organisation', 
      'profiles' => 'ProjectBundle\Entity\User\Profile', 
      'csrf' => true, 
     )); 

    } 
} 

如果有人有解决方案。

预先感谢您!

+0

[Doctrine 2 @Gedmo \ SoftDeleteable和唯一字段]的可能重复(https://stackoverflow.com/questions/33533761/doctrine-2-gedmo-softdeleteable-and-unique-fields) –

+0

错误几乎完全相同但提出的解决方案不起作用,我仍然有SQL异常。 –

回答

0

你有没有尝试过这样的:

/** 
* @ORM\Entity(repositoryClass="ProjectBundle\Repository\User\UserRepository") 
* @Gedmo\SoftDeleteable(fieldName="deletedAt") 
* @ORM\Entity 
* @UniqueEntity(fields={"email", "username"}, groups={"registration"}) 
* @ORM\Table(name="user") 
*/ 

但要确保你有一个电子邮件地址和用户名的唯一索引。

+0

您的解决方案仅适用于DEV。当我更新PROD的更改时,异常仍然存在。 (数据库已经准备好了索引) –

0

目前,@ CarcaBot的响应仅适用于DEV,在文件完全相同的情况下,更新不会在PROD中更改我的问题以及数据库。

一个想法?