src/Entity/Prospect.php line 31

Open in your IDE?
  1. <?php
  2. namespace App\Entity;
  3. use App\Utils\Formatter;
  4. use App\Validator as McaAssert;
  5. use Doctrine\Common\Collections\ArrayCollection;
  6. use Doctrine\Common\Collections\Collection;
  7. use Doctrine\Common\Collections\Criteria;
  8. use Doctrine\ORM\Mapping as ORM;
  9. use Gedmo\Mapping\Annotation as Gedmo;
  10. use phpDocumentor\Reflection\Types\Integer;
  11. use Symfony\Component\Validator\Constraints as Assert;
  12. use ApiPlatform\Core\Annotation\ApiResource;
  13. use Symfony\Component\Serializer\Annotation\Groups;
  14. /**
  15.  * @ORM\Entity(repositoryClass="App\Repository\ProspectRepository")
  16.  * @ORM\EntityListeners({"App\Listener\ProspectListener"})
  17.  * @ApiResource(
  18.  *     collectionOperations={
  19.             "post"={
  20.  *              "validation_groups"={"Default", "API"}
  21.  *          },
  22.  *
  23.  *     },
  24.  *     itemOperations={"get"={"security"="is_granted('ROLE_API')"}},
  25.  *     normalizationContext={"groups"={"prospect:read"}},
  26.  *     denormalizationContext={"groups"={"prospect:write"}}
  27.  * )
  28.  */
  29. class Prospect implements MediaoptionDeliverable
  30. {
  31.     const TYPE_APPOINTMENT 'appointment';
  32.     const TYPE_CHECKUP 'checkup';
  33.     const ACQUISITION_MODE_API 'api';
  34.     /**
  35.      * @ORM\Id()
  36.      * @ORM\GeneratedValue()
  37.      * @ORM\Column(type="integer")
  38.      */
  39.     private $id;
  40.     /**
  41.      * @ORM\Column(type="datetime")
  42.      * @Gedmo\Timestampable(on="create")
  43.      */
  44.     private $created;
  45.     /**
  46.      * @ORM\Column(type="smallint", nullable=true)
  47.      * @Assert\NotBlank(groups={"API"})
  48.      * @Groups({"prospect:write"})
  49.      */
  50.     private $gender;
  51.     /**
  52.      * @ORM\Column(type="string", length=255)
  53.      * @Groups({"prospect:read", "prospect:write"})
  54.      * @Assert\NotBlank
  55.      * @Assert\Length(
  56.      *      min = 2,
  57.      *      max = 50,
  58.      * )
  59.      * @Assert\Regex(
  60.      *      pattern="/^[A-Za-zÀ-úœ'\-\s]*$/",
  61.      *      message="Le prénom n'est pas valide"
  62.      * )
  63.      */
  64.     private $firstname;
  65.     /**
  66.      * @ORM\Column(type="string", length=255)
  67.      * @Groups({"prospect:read", "prospect:write"})
  68.      * @Assert\NotBlank
  69.      * @Assert\Regex(
  70.      *      pattern="/^[A-Za-zÀ-úœ'\-\s]*$/",
  71.      *      message="Le nom n'est pas valide"
  72.      * )
  73.      * @Assert\Length(
  74.      *      min = 2,
  75.      *      max = 50,
  76.      * )
  77.      */
  78.     private $lastname;
  79.     /**
  80.      * @ORM\Column(type="string", length=255, nullable=true)
  81.      * @Groups({"prospect:read", "prospect:write"})
  82.      * @Assert\NotBlank()
  83.      * @Assert\Length(
  84.      *      min = 2,
  85.      *      max = 200,
  86.      * )
  87.      */
  88.     private $address;
  89.     /**
  90.      * @ORM\Column(type="string", length=5)
  91.      * @Assert\NotBlank()
  92.      * @Assert\Regex(
  93.      *      pattern="/^(([0-8][0-9])|(9[0-5])|(2[ab]))[0-9]{3}$/",
  94.      *      message="Le code postal n'est pas valide"
  95.      * )
  96.      * @Groups({"prospect:read", "prospect:write"})
  97.      */
  98.     private $postalcode;
  99.     /**
  100.      * @ORM\Column(type="string", length=255, nullable=true)
  101.      * @Assert\Length(
  102.      *      min = 2,
  103.      *      max = 50,
  104.      * )
  105.      * @Assert\NotBlank(groups={"API"})
  106.      * @Groups({"prospect:read", "prospect:write"})
  107.      */
  108.     private $city;
  109.     /**
  110.      * @ORM\Column(type="string", length=255, nullable=true)
  111.      * @Assert\NotBlank
  112.      * @Assert\Regex ("/^\w([\w\-\_\+\.\d]+?)+@[\w-]+(\.[A-Za-z]{2,4}){1,2}$/")
  113.      * @Assert\Email(
  114.      *     message = "L'email '{{ value }}' n'est pas valide",
  115.      *     mode = "strict"
  116.      * )
  117.      * @Groups({"prospect:read", "prospect:write"})
  118.      */
  119.     private $email;
  120.     /**
  121.      * @ORM\Column(type="string", length=255, nullable=true)
  122.      * @Assert\NotBlank
  123.      * @McaAssert\ValidPhoneNumber
  124.      * @Groups({"prospect:read", "prospect:write"})
  125.      */
  126.     private $phoneNumber;
  127.     /**
  128.      * @ORM\Column(type="string", length=4, nullable=true)
  129.      * @Assert\NotBlank()
  130.      * @Assert\Regex(pattern="/^(19|20)\d{2}$/", message="L'année de naissance n'est pas valide.")
  131.      * @Groups({"prospect:read", "prospect:write"})
  132.      */
  133.     private $yearOfBirth;
  134.     /**
  135.      * @ORM\Column(type="boolean")
  136.      * @Groups({"prospect:read", "prospect:write"})
  137.      */
  138.     private $isPrivacy=0;
  139.     /**
  140.      * @ORM\Column(type="boolean", nullable=true)
  141.      * @Groups({"prospect:read", "prospect:write"})
  142.      */
  143.     private $isOptin;
  144.     /**
  145.      * @ORM\Column(type="boolean", nullable=true)
  146.      * @Groups({"prospect:read", "prospect:write"})
  147.      */
  148.     private $isPartnerOffer;
  149.     /**
  150.      * @ORM\Column(type="string", length=255)
  151.      * @Groups({"prospect:read", "prospect:write"})
  152.      */
  153.     private $request;
  154.     /**
  155.      * @ORM\ManyToOne(targetEntity="App\Entity\PhoneValidation", inversedBy="prospect", cascade={"persist", "remove"})
  156.      * @ORM\JoinColumn(nullable=true)
  157.      */
  158.     private $phoneValidation;
  159.     /**
  160.      * @ORM\OneToMany(targetEntity="App\Entity\ProspectOnStore", mappedBy="prospect", cascade={"persist", "remove"})
  161.      */
  162.     private $prospectsOnStore;
  163.     /**
  164.      * @ORM\OneToMany(targetEntity="App\Entity\MediaoptinDelivery", mappedBy="prospect", cascade={"persist", "remove"})
  165.      */
  166.     private $mediaoptinDeliveries;
  167.     /**
  168.      * Mode d'acquisition du lead (emailing, facebook, ...)
  169.      *
  170.      * @ORM\Column(type="string", length=255, nullable=true)
  171.      * @Groups({"prospect:write"})
  172.      */
  173.     private $acquisitionMode;
  174.     /**
  175.      * Base emailing de provenance du lead
  176.      *
  177.      * @ORM\Column(type="string", length=255, nullable=true)
  178.      * @Assert\NotBlank(groups={"API"})
  179.      * @Groups({"prospect:write"})
  180.      */
  181.     private $acquisitionBase;
  182.     /**
  183.      * Url de provenance du lead (dernière URL avant persist)
  184.      *
  185.      * @ORM\Column(type="string", length=255, nullable=true)
  186.      * @Groups({"prospect:write"})
  187.      */
  188.     private $acquisitionUrl;
  189.     /**
  190.      * Meta keyword URL
  191.      * @ORM\Column(type="string", length=255, nullable=true)
  192.      * @Groups({"prospect:write"})
  193.      */
  194.     private $acquisitionKeyword;
  195.     /**
  196.      * @ORM\Column(type="float", nullable=true)
  197.      */
  198.     private $latitude;
  199.     /**
  200.      * @ORM\Column(type="float", nullable=true)
  201.      */
  202.     private $longitude;
  203.     /**
  204.      * @var string
  205.      * @ORM\Column(type="string", length=255, nullable=true)
  206.      */
  207.     private $locationType;
  208.     /**
  209.      * @var string
  210.      * @ORM\Column(type="string", length=255, nullable=true)
  211.      */
  212.     private $countryCode;
  213.     /**
  214.      * @var boolean
  215.      * @ORM\Column(type="boolean")
  216.      */
  217.     private $isDropped false;
  218.     /**
  219.      * @ORM\OneToMany(targetEntity="App\Entity\ProspectDuplicate", mappedBy="prospect", cascade={"remove"})
  220.      */
  221.     private $prospectDuplicates;
  222.     /**
  223.      * @ORM\Column(type="integer", nullable=true)
  224.      */
  225.     private $duplicateState;
  226.     /**
  227.      * @ORM\Column(type="boolean", nullable=true)
  228.      * @Groups({"prospect:write"})
  229.      * @var boolean
  230.      */
  231.     private $isOrlPrescription;
  232.     /**
  233.      * @ORM\Column(type="boolean", nullable=true)
  234.      * @Groups({"prospect:write"})
  235.      * @var boolean
  236.      */
  237.     private $isEquipped;
  238.     /**
  239.      * @ORM\Column(type="boolean", nullable=true)
  240.      * @Groups({"prospect:write"})
  241.      * @var boolean
  242.      */
  243.     private $isThirdPerson;
  244.     /**
  245.      * @ORM\OneToOne(targetEntity=ProspectQualification::class, cascade={"persist", "remove"}, inversedBy="prospect")
  246.      */
  247.     private $qualification;
  248.     /**
  249.      * Add checkmail boolean on prospect: yes->email validated , no->email invalid, null->no validation has been done
  250.      * @ORM\Column(type="boolean", nullable=true)
  251.      */
  252.     private $checkmail;
  253.     /**
  254.      * @ORM\Column(type="boolean")
  255.      */
  256.     private bool $isUsingDoctolib=false;
  257.     /**
  258.      * @ORM\Column(type="boolean", nullable=true)
  259.      * @Groups({"prospect:write"})
  260.      */
  261.     private ?bool $isQualifiedExternally=false;
  262.     /**
  263.      * MCA-784: IDs of admin for force delivery (ex: "123" ou "123,456")
  264.      * virtual field (non-persist) - the value is persist on POS
  265.      * @Groups({"prospect:write"})
  266.      */
  267.     private ?string $forceDeliveredAdminId null;
  268.     public function __construct()
  269.     {
  270.         $this->prospectsOnStore = new ArrayCollection();
  271.         $this->mediaoptinDeliveries = new ArrayCollection();
  272.         $this->prospectDuplicates = new ArrayCollection();
  273.     }
  274.     /**
  275.      * Représente l'entité par défault
  276.      * @return string
  277.      */
  278.     public function __toString(){
  279.         return 'Prospect ['.$this->getId().']';
  280.     }
  281.     /**
  282.      * Obtenir l'adresse complète
  283.      * @return string
  284.      */
  285.     public function getFullAddress() {
  286.         return $this->getAddress() . ' ' $this->getPostalcode() . ' ' $this->getCity();
  287.     }
  288.     /**
  289.      * Représente l'entité dans le BO
  290.      * @return string
  291.      */
  292.     public function getLabel(){
  293.         return '#'.$this->getId();
  294.     }
  295.     public function getId(): ?int
  296.     {
  297.         return $this->id;
  298.     }
  299.     public function getGender(): ?int
  300.     {
  301.         return $this->gender;
  302.     }
  303.     public function setGender(?int $gender): self
  304.     {
  305.         $this->gender $gender;
  306.         return $this;
  307.     }
  308.     public function getFirstname(): ?string
  309.     {
  310.         return $this->firstname;
  311.     }
  312.     public function setFirstname(?string $firstname): self
  313.     {
  314.         $this->firstname $firstname;
  315.         return $this;
  316.     }
  317.     public function getLastname(): ?string
  318.     {
  319.         return $this->lastname;
  320.     }
  321.     public function setLastname(?string $lastname): self
  322.     {
  323.         $this->lastname $lastname;
  324.         return $this;
  325.     }
  326.     public function getFullname(): ?string
  327.     {
  328.         return ucfirst($this->firstname).' '.ucfirst($this->lastname);
  329.     }
  330.     public function getEmail(): ?string
  331.     {
  332.         return $this->email;
  333.     }
  334.     public function setEmail(?string $email): self
  335.     {
  336.         $this->email $email;
  337.         return $this;
  338.     }
  339.     public function getPhoneNumber(): ?string
  340.     {
  341.         return $this->phoneNumber;
  342.     }
  343.     public function setPhoneNumber(?string $phoneNumber): self
  344.     {
  345.         $phoneNumber Formatter::phoneNumberFrenchFormat($phoneNumber);
  346.         $this->phoneNumber $phoneNumber;
  347.         return $this;
  348.     }
  349.     public function getPhoneNumberFormatted() {
  350.         return wordwrap($this->getPhoneNumber() , ' ' true );
  351.     }
  352.     public function getYearOfBirth(): ?string
  353.     {
  354.         return $this->yearOfBirth;
  355.     }
  356.     public function setYearOfBirth(?string $yearOfBirth): self
  357.     {
  358.         //prevent insertion of non numeri value (ex: 1994-05-17). if not numeric field remains blank
  359.         $yearOfBirth substr($yearOfBirth,0,4);
  360.         if(is_numeric($yearOfBirth)){
  361.             $this->yearOfBirth $yearOfBirth;
  362.         }
  363.         return $this;
  364.     }
  365.     public function getDateFromYearOfBirth(): ?\DateTimeInterface {
  366.         return new \DateTime($this->getYearOfBirth() . '-01-01');
  367.     }
  368.     public function getAge(): int {
  369.         $now = new \DateTime();
  370.         return $this->getDateFromYearOfBirth()->diff($now)->y;
  371.     }
  372.     public function getRequest(): ?string
  373.     {
  374.         return $this->request;
  375.     }
  376.     public function setRequest(string $request): self
  377.     {
  378.         $this->request $request;
  379.         return $this;
  380.     }
  381.     public function getIsPrivacy(): ?bool
  382.     {
  383.         return $this->isPrivacy;
  384.     }
  385.     public function setIsPrivacy(bool $isPrivacy): self
  386.     {
  387.         $this->isPrivacy $isPrivacy;
  388.         return $this;
  389.     }
  390.     public function getIsOptin(): ?bool
  391.     {
  392.         return $this->isOptin;
  393.     }
  394.     public function setIsOptin(bool $isOptin): self
  395.     {
  396.         $this->isOptin $isOptin;
  397.         return $this;
  398.     }
  399.     public function getIsPartnerOffer(): ?bool
  400.     {
  401.         return $this->isPartnerOffer;
  402.     }
  403.     public function setIsPartnerOffer(bool $isPartnerOffer): self
  404.     {
  405.         $this->isPartnerOffer $isPartnerOffer;
  406.         return $this;
  407.     }
  408.     public function getAddress(): ?string
  409.     {
  410.         return $this->address;
  411.     }
  412.     public function setAddress(?string $address): self
  413.     {
  414.         $this->address $address;
  415.         return $this;
  416.     }
  417.     public function getPostalcode(): ?string
  418.     {
  419.         return $this->postalcode;
  420.     }
  421.     public function setPostalcode(?string $postalcode): self
  422.     {
  423.         if(strlen($postalcode) === 4) {
  424.             $this->postalcode str_pad($postalcode5'0'STR_PAD_LEFT);
  425.         } else {
  426.             $this->postalcode $postalcode;
  427.         }
  428.         return $this;
  429.     }
  430.     public function getCity(): ?string
  431.     {
  432.         return $this->city;
  433.     }
  434.     public function setCity(?string $city): self
  435.     {
  436.         $this->city $city;
  437.         return $this;
  438.     }
  439.     public function getPhoneValidation(): ?PhoneValidation
  440.     {
  441.         return $this->phoneValidation;
  442.     }
  443.     public function setPhoneValidation(?PhoneValidation $phoneValidation): self
  444.     {
  445.         $this->phoneValidation $phoneValidation;
  446.         return $this;
  447.     }
  448.     public function getExportProspectsOnStore()
  449.     {
  450.         $exportStores = [];
  451.         foreach ($this->getProspectsOnStore() as $key => $val) {
  452.             $str $val->getStore()->getName() . ' (' $val->getStore()->getZipCode(). ')';
  453.             if($val->getIsDemandForThird()){
  454.                 $str .= " <span class=\"badge badge-warning\">demande pour un tiers</span>";
  455.             }
  456.             $exportStores[] = $str;
  457.         }
  458.         return join(' , '$exportStores);
  459.     }
  460.     /**
  461.      * @return Collection|ProspectOnStore[]
  462.      */
  463.     public function getProspectsOnStore(): Collection
  464.     {
  465.         return $this->prospectsOnStore;
  466.     }
  467.     /**
  468.      * @param Store $store
  469.      * @return ?ProspectOnStore
  470.      */
  471.     public function getProspectOnStore(Store $store): ?ProspectOnStore
  472.     {
  473.         $criteria Criteria::create() ->andWhere(Criteria::expr()->eq('store'$store))->setMaxResults(1);
  474.         $pos $this->prospectsOnStore->matching($criteria);
  475.         if($pos->isEmpty()){
  476.             return null;
  477.         }else{
  478.             return $pos->first();
  479.         }
  480.     }
  481.     /**
  482.      * @return int
  483.      */
  484.     public function getNbOfProspectsOnStore(): int
  485.     {
  486.         return $this->prospectsOnStore->count();
  487.     }
  488.     public function addProspectsOnStore(ProspectOnStore $prospectsOnStore): self
  489.     {
  490.         if (!$this->prospectsOnStore->contains($prospectsOnStore)) {
  491.             $this->prospectsOnStore[] = $prospectsOnStore;
  492.             $prospectsOnStore->setProspect($this);
  493.         }
  494.         return $this;
  495.     }
  496.     public function removeProspectsOnStore(ProspectOnStore $prospectsOnStore): self
  497.     {
  498.         if ($this->prospectsOnStore->contains($prospectsOnStore)) {
  499.             $this->prospectsOnStore->removeElement($prospectsOnStore);
  500.             // set the owning side to null (unless already changed)
  501.             if ($prospectsOnStore->getProspect() === $this) {
  502.                 $prospectsOnStore->setProspect(null);
  503.             }
  504.         }
  505.         return $this;
  506.     }
  507.     public function getCreated(): ?\DateTimeInterface
  508.     {
  509.         return $this->created;
  510.     }
  511.     public function setCreated(\DateTimeInterface $created): self
  512.     {
  513.         $this->created $created;
  514.         return $this;
  515.     }
  516.     /**
  517.      * @return Collection|MediaoptinDelivery[]
  518.      */
  519.     public function getMediaoptinDeliveriesOwnOrByStore(): Collection
  520.     {
  521.         if(empty($this->prospectsOnStore)){
  522.             return $this->mediaoptinDeliveries;
  523.         }else{
  524.             $deliveries = [];
  525.             foreach ($this->prospectsOnStore as $pos){
  526.                 $deliveries array_merge($deliveries$pos->getMediaoptinDeliveries()->toArray() );
  527.             }
  528.             return new ArrayCollection($deliveries);
  529.         }
  530.     }
  531.     public function getExportMediaoptinDeliveriesOwnOrByStore()
  532.     {
  533.         //dump($this->getMediaoptinDeliveriesOwnOrByStore());
  534.         $exportDeliveries = [];
  535.         foreach ($this->getMediaoptinDeliveriesOwnOrByStore() as $key => $val) {
  536.             if($val->getDeliveryDate()){
  537.                 $str $val->getDeliveryDate()->format('d/m/Y');
  538.             }else{
  539.                 $str $val->getResponse();
  540.             }
  541.             $exportDeliveries[] = $str;
  542.         }
  543.         return join(', '$exportDeliveries);
  544.     }
  545.     /**
  546.      * Display the label of deliveries (for export)
  547.      * @return string|null
  548.      */
  549.     public function getDeliveryStatusLabel(): ?string {
  550.         $deliveries $this->getMediaoptinDeliveriesOwnOrByStore();
  551.         if(count($deliveries)==0){
  552.             return 'multi';
  553.         }
  554.         foreach ($deliveries as $delivery){
  555.             if($delivery->isSuccessful()){
  556.                 return 'livré';
  557.             }else{
  558.                 return 'erreur';
  559.             }
  560.         }
  561.         return null;
  562.     }
  563.     /**
  564.      * @return Collection|MediaoptinDelivery[]
  565.      */
  566.     public function getMediaoptinDeliveries(): Collection
  567.     {
  568.         return $this->mediaoptinDeliveries;
  569.     }
  570.     public function addMediaoptinDelivery(MediaoptinDelivery $mediaoptinDelivery): self
  571.     {
  572.         if (!$this->mediaoptinDeliveries->contains($mediaoptinDelivery)) {
  573.             $this->mediaoptinDeliveries[] = $mediaoptinDelivery;
  574.             $mediaoptinDelivery->setProspect($this);
  575.         }
  576.         return $this;
  577.     }
  578.     public function removeMediaoptinDelivery(MediaoptinDelivery $mediaoptinDelivery): self
  579.     {
  580.         if ($this->mediaoptinDeliveries->contains($mediaoptinDelivery)) {
  581.             $this->mediaoptinDeliveries->removeElement($mediaoptinDelivery);
  582.             // set the owning side to null (unless already changed)
  583.             if ($mediaoptinDelivery->getProspect() === $this) {
  584.                 $mediaoptinDelivery->setProspect(null);
  585.             }
  586.         }
  587.         return $this;
  588.     }
  589.     public function getAcquisitionMode(): ?string
  590.     {
  591.         return $this->acquisitionMode;
  592.     }
  593.     public function setAcquisitionMode(?string $acquisitionMode): self
  594.     {
  595.         $this->acquisitionMode $acquisitionMode;
  596.         return $this;
  597.     }
  598.     public function getAcquisitionBase(): ?string
  599.     {
  600.         return $this->acquisitionBase;
  601.     }
  602.     public function setAcquisitionBase(?string $acquisitionBase): self
  603.     {
  604.         $this->acquisitionBase $acquisitionBase;
  605.         return $this;
  606.     }
  607.     public function getAcquisitionUrl(): ?string
  608.     {
  609.         return $this->acquisitionUrl;
  610.     }
  611.     public function setAcquisitionUrl(?string $acquisitionUrl): self
  612.     {
  613.         $this->acquisitionUrl $acquisitionUrl;
  614.         return $this;
  615.     }
  616.     public function getLatitude(): ?float
  617.     {
  618.         return $this->latitude;
  619.     }
  620.     public function setLatitude(?float $latitude): self
  621.     {
  622.         $this->latitude $latitude;
  623.         return $this;
  624.     }
  625.     public function getLongitude(): ?float
  626.     {
  627.         return $this->longitude;
  628.     }
  629.     public function setLongitude(?float $longitude): self
  630.     {
  631.         $this->longitude $longitude;
  632.         return $this;
  633.     }
  634.     public function getLocationType(): ?string
  635.     {
  636.         return $this->locationType;
  637.     }
  638.     public function setLocationType(?string $locationType): self
  639.     {
  640.         $this->locationType $locationType;
  641.         return $this;
  642.     }
  643.     public function getCountryCode(): ?string
  644.     {
  645.         return $this->countryCode;
  646.     }
  647.     public function setCountryCode(?string $countryCode): self
  648.     {
  649.         $this->countryCode $countryCode;
  650.         return $this;
  651.     }
  652.     public function getIsDropped(): ?bool
  653.     {
  654.         return $this->isDropped;
  655.     }
  656.     public function setIsDropped(bool $isDropped): self
  657.     {
  658.         $this->isDropped $isDropped;
  659.         return $this;
  660.     }
  661.     public function getLeadNumber(){
  662.         return md5($this->getEmail());
  663.     }
  664.     /**
  665.      * @return Collection|ProspectDuplicate[]
  666.      */
  667.     public function getProspectDuplicates(): Collection
  668.     {
  669.         return $this->prospectDuplicates;
  670.     }
  671.     /**
  672.      * @return integer
  673.      */
  674.     public function getNbOfProspectDuplicates(): int
  675.     {
  676.         return $this->prospectDuplicates->count();
  677.     }
  678.     public function addProspectDuplicate(ProspectDuplicate $prospectDuplicate): self
  679.     {
  680.         if (!$this->prospectDuplicates->contains($prospectDuplicate)) {
  681.             $this->prospectDuplicates[] = $prospectDuplicate;
  682.             $prospectDuplicate->setProspect($this);
  683.         }
  684.         return $this;
  685.     }
  686.     public function removeProspectDuplicate(ProspectDuplicate $prospectDuplicate): self
  687.     {
  688.         if ($this->prospectDuplicates->contains($prospectDuplicate)) {
  689.             $this->prospectDuplicates->removeElement($prospectDuplicate);
  690.             // set the owning side to null (unless already changed)
  691.             if ($prospectDuplicate->getProspect() === $this) {
  692.                 $prospectDuplicate->setProspect(null);
  693.             }
  694.         }
  695.         return $this;
  696.     }
  697.     public function getDuplicateState(): ?int
  698.     {
  699.         return $this->duplicateState;
  700.     }
  701.     public function setDuplicateState($state): self
  702.     {
  703.         $this->duplicateState $state;
  704.         return $this;
  705.     }
  706.     public function getIsOrlPrescription(): ?bool
  707.     {
  708.         return $this->isOrlPrescription;
  709.     }
  710.     public function setIsOrlPrescription(?bool $isOrlPrescription): self
  711.     {
  712.         $this->isOrlPrescription $isOrlPrescription;
  713.         return $this;
  714.     }
  715.     public function getIsEquipped(): ?bool
  716.     {
  717.         return $this->isEquipped;
  718.     }
  719.     public function setIsEquipped(?bool $isEquipped): self
  720.     {
  721.         $this->isEquipped $isEquipped;
  722.         return $this;
  723.     }
  724.     public function getIsThirdPerson(): ?bool
  725.     {
  726.         return $this->isThirdPerson;
  727.     }
  728.     public function setIsThirdPerson(?bool $isThirdPerson): self
  729.     {
  730.         $this->isThirdPerson $isThirdPerson;
  731.         return $this;
  732.     }
  733.     /**
  734.      * Export for Sonata Admin
  735.      * @return string
  736.      */
  737.     public function getExportIsOrlPrescription() {
  738.         if(isset($this->isOrlPrescription)) {
  739.             return $this->getIsOrlPrescription() ? "Oui" "Non";
  740.         } else {
  741.             return "Non renseigné";
  742.         }
  743.     }
  744.     /**
  745.      * Export for Sonata Admin
  746.      * @return string
  747.      */
  748.     public function getExportIsEquipped() {
  749.         if(isset($this->isEquipped)) {
  750.             return $this->getIsEquipped() ? "Oui" "Non";
  751.         } else {
  752.             return "Non renseigné";
  753.         }
  754.     }
  755.     /**
  756.      * Export for Sonata Admin
  757.      * @return string
  758.      */
  759.     public function getExportIsThirdPerson() {
  760.         if(isset($this->isThirdPerson)) {
  761.             return $this->getIsThirdPerson() ? "Oui" "Non";
  762.         } else {
  763.             return "Non renseigné";
  764.         }
  765.     }
  766.     public function getQualification(): ?ProspectQualification
  767.     {
  768.         return $this->qualification;
  769.     }
  770.     public function setQualification(?ProspectQualification $qualification): self
  771.     {
  772.         $this->qualification $qualification;
  773.         return $this;
  774.     }
  775.     public function getCheckmail(): ?bool
  776.     {
  777.         return $this->checkmail;
  778.     }
  779.     public function setCheckmail(?bool $checkmail): self
  780.     {
  781.         $this->checkmail $checkmail;
  782.         return $this;
  783.     }
  784.     public function getAcquisitionKeyword(): ?string
  785.     {
  786.         return $this->acquisitionKeyword;
  787.     }
  788.     public function setAcquisitionKeyword(?string $acquisitionKeyword): self
  789.     {
  790.         $this->acquisitionKeyword $acquisitionKeyword;
  791.         return $this;
  792.     }
  793.     /**
  794.      * @return bool
  795.      */
  796.     public function isUsingDoctolib(): bool
  797.     {
  798.         return $this->isUsingDoctolib;
  799.     }
  800.     /**
  801.      * @param bool $isUsingDoctolib
  802.      */
  803.     public function setIsUsingDoctolib(bool $isUsingDoctolib): void
  804.     {
  805.         $this->isUsingDoctolib $isUsingDoctolib;
  806.     }
  807.     public function getIsQualifiedExternally(): ?bool
  808.     {
  809.         return $this->isQualifiedExternally;
  810.     }
  811.     public function setIsQualifiedExternally($isQualifiedExternally): void
  812.     {
  813.         $this->isQualifiedExternally boolval($isQualifiedExternally);
  814.     }
  815.     /**
  816.      * MCA-784: Get force delivered admin IDs
  817.      */
  818.     public function getForceDeliveredAdminId(): ?string
  819.     {
  820.         return $this->forceDeliveredAdminId;
  821.     }
  822.     /**
  823.      * MCA-784: Set force delivered admin IDs (ex: "123" ou "123,456")
  824.      */
  825.     public function setForceDeliveredAdminId(?string $forceDeliveredAdminId): self
  826.     {
  827.         // Validation : IDs numériques séparés par virgules
  828.         if ($forceDeliveredAdminId !== null && !preg_match('/^[0-9]+(,[0-9]+)*$/'$forceDeliveredAdminId)) {
  829.             $forceDeliveredAdminId null;
  830.         }
  831.         $this->forceDeliveredAdminId $forceDeliveredAdminId;
  832.         return $this;
  833.     }
  834. }