Top ad position

Constraint on two unique fields using @UnityEntity annotation

Started 2 years ago by M R Alam in Programming Language, PHP

Constraint on two unique fields using @UnityEntity annotation

Body

<?php

**
* @ORM\Entity(repositoryClass=SupplierRepository::class)
* @UniqueEntity("siretNumber",repositoryMethod="getSupplierByPerimeter", message="Le numéro de SIRET est déjà utilisé.")
*/
class Supplier
{
   /**
    * @ORM\Id
    * @ORM\GeneratedValue
    * @ORM\Column(type="integer")
    */
   private $id;

   /**
    * @Assert\NotBlank(allowNull=true)
    * @Assert\Regex(pattern = "/^[0-9]*$/", message="Seul les chiffres sont autorisés.")
    * @Assert\Length(
    *      min=14,
    *      max=14,
    *      exactMessage = "Le numéro de SIRET doit faire exactement 14 chiffres (SIREN (9) et NIC (5))"
    * )
    * @ORM\Column(type="string", length=14, nullable=true, unique=true)
    */
   private $siretNumber;

  * @ORM\ManyToOne(targetEntity=Perimeter::class, inversedBy="suppliers")
    * @ORM\JoinColumn(nullable=false)
    */
   private $perimeter;
}

Here I want to check if the $siretNumber is unique BUT ONLY if the $perimeter already have a Supplier associated with this siretNumber. Meaning that two perimeter can have the same Supplier with the same siretNumber but that one Perimeter can have only one unique siretNumber for each of its suppliers.

I tried to use the repositoryMethod like so:

  • @UniqueEntity("siretNumber",repositoryMethod="getSupplierByPerimeter", message="Le numéro de SIRET est déjà utilisé.")

The method:

<?php

namespace App<span class="hljs-title class_">Repository;

use App<span class="hljs-title">Entity<span class="hljs-title">Supplier; use App<span class="hljs-title">Repository<span class="hljs-title">PerimeterRepository; use Doctrine<span class="hljs-title">Persistence<span class="hljs-title">ManagerRegistry; use Symfony<span class="hljs-title">Component<span class="hljs-title">Security<span class="hljs-title">Core<span class="hljs-title">Security; use Doctrine<span class="hljs-title">Bundle<span class="hljs-title">DoctrineBundle<span class="hljs-title">Repository<span class="hljs-title">ServiceEntityRepository;

/**

  • @method Supplier|null find($id, $lockMode = null, $lockVersion = null)

  • @method Supplier|null findOneBy(array $criteria, array $orderBy = null)

  • @method Supplier[] findAll()

  • @method Supplier[] findBy(array $criteria, array $orderBy = null, $limit = null, $offset = null) */ class SupplierRepository extends ServiceEntityRepository { private $security; private $perimeterRepository;

    public function __construct(ManagerRegistry $registry, Security $security,PerimeterRepository $perimeterRepository) { parent::__construct($registry, Supplier::class); $this->security = $security; $this->perimeterRepository = $perimeterRepository; }

    /**

    • @return Supplier[] Returns an array of Supplier objects */ public function getSupplierByPerimeter() { $perimeter = $this->perimeterRepository->findOneBy(["label" => $this->security->getUser()->getOptions()["perimeter"]]);

      return $this->createQueryBuilder('s') ->where('s.perimeter = :perimeter') ->setParameter('perimeter', $perimeter) ->getQuery() ->getResult() ; }

The problem is that UniqueEntity seems to still check in all the Supplier table and not in the array return by getSupplierByPerimeter() so I'm still geting the validation error even if the siretNumber is associated with another Perimeter and not the current Perimeter while creating a new supplier.

Maybe I'm not using the repositoryMethod right but I don't know otherwise how to do what I want.

Does someone have an idea ?

  • No one is replied to this thread yet. Be first to reply!
Bottom ad position