src/Controller/Front/InscriptionController.php line 61
<?phpnamespace App\Controller\Front;use JsonException;use App\Entity\Common\Adresse;use App\Entity\Gestiform\Admin\Profil;use App\Entity\Gestiform\Formations\Dossier\Dossier;use App\Entity\Gestiform\Formations\Dossier\DossierAnnexes;use App\Entity\Gestiform\Formations\Dossier\HistoriqueDossier;use App\Entity\Gestiform\Formations\Entreprise\Contact;use App\Entity\Gestiform\Formations\Entreprise\Entreprise;use App\Entity\Gestiform\Formations\Session\Planning\Planning;use App\Enums\TypeActifEnum;use App\Form\Gestiform\Formations\Dossier\DossierInfosType;use App\Form\Gestiform\Front\Inscription\EntrepriseInfosType;use App\Service\Misc\ModelDocumentService;use App\Service\Admin\MasterlistelgService;use App\Service\Admin\ProfilService;use App\Service\Admin\Users\UserService;use App\Service\Formations\Catalogue\ParcoursService;use App\Service\Formations\Dossier\DossierService;use App\Service\Formations\Entreprise\EntrepriseService;use App\Service\Formations\Sessions\SessionParcours\SessionParcoursService;use App\Service\Front\InscriptionService;use App\Service\Gestiform\Formations\Commercial\DossierToLeadService;use App\Entity\Gestiform\Admin\Candidature\ReceptionParcoursEmploye;use App\Entity\Gestiform\Formations\Catalogue\Parcours\Parcours;use App\Entity\Gestiform\Users\Employe;use Doctrine\ORM\NonUniqueResultException;use Doctrine\ORM\EntityManagerInterface;use Symfony\Component\Mailer\Exception\TransportExceptionInterface;use Symfony\Component\Mime\Exception\RfcComplianceException;use Twig\Error\LoaderError;use Twig\Error\RuntimeError;use Twig\Error\SyntaxError;use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;use Symfony\Component\HttpFoundation\Request;use Symfony\Component\HttpFoundation\Response;use Symfony\Component\Routing\Attribute\Route;#[Route(path: '/inscription', name: 'inscription_', host: '%front_domain%')]class InscriptionController extends AbstractController{public function __construct(private readonly DossierService $dossierService,private readonly EntityManagerInterface $em,private readonly MasterlistelgService $masterlistelgService,private readonly ParcoursService $parcoursService,private readonly SessionParcoursService $sessionParcoursService,private readonly InscriptionService $inscriptionService,private readonly DossierToLeadService $dossierToLeadService,private readonly ModelDocumentService $modelDocumentService,private readonly ProfilService $profilService,private readonly UserService $userService,private readonly EntrepriseService $entrepriseService){}private function resolveDefaultEmployeForParcours(?Parcours $parcours): ?Employe{if (!$parcours) {return null;}$tryResolve = function (Parcours $p): ?Employe {$qb = $this->em->createQueryBuilder();$qb->select('rpe')->from(ReceptionParcoursEmploye::class, 'rpe')->innerJoin('rpe.reception', 'r')->innerJoin('r.parcours', 'rpp')->innerJoin('rpp.parcours', 'pp')->andWhere('pp = :parcours')->andWhere('(r.archive = false OR r.archive IS NULL)')->setParameter('parcours', $p)->addOrderBy('r.id', 'ASC')->addOrderBy('rpe.ordre', 'ASC')->addOrderBy('rpe.id', 'ASC')->setMaxResults(1);/** @var ReceptionParcoursEmploye|null $row */$row = $qb->getQuery()->getOneOrNullResult();return $row?->getEmploye();};$employe = $tryResolve($parcours);if ($employe) {return $employe;}$parent = $parcours->getParent();if ($parent) {return $tryResolve($parent);}return null;}#[Route(path: '/prospect', name: 'prospect')]public function profilProspect(): Response{$profils = $this->profilService->getRepository()->findBy(['archived' => false]);return $this->render('front/inscription/prospect/inscription.html.twig', ['profils' => $profils,'vueData' => [],]);}#[Route(path: '/postulant', name: 'postulant')]public function inscriptionPostulant(): Response{$addPostulantForm = $this->createForm(DossierInfosType::class,new Dossier(),['action' => $this->generateUrl("inscription_add_postulant",),]);return $this->render('front/inscription/postulant/inscription.html.twig', ['addPostulantForm' => $addPostulantForm->createView(),'vueData' => []]);}/*** @throws NonUniqueResultException*/#[Route(path: '/{id}/valider-devis', name: 'valider_devis', requirements: ['id' => '\d+'])]public function traiterDevis(Entreprise $entreprise, Request $request): Response{$modules = $request->request->get('modules', []);$this->inscriptionService->addDevisEntreprise($entreprise, $modules);return $this->redirectToRoute('inscription_profil');}#[Route(path: '/{id}/prospect', name: 'prospect_inscription', requirements: ['id' => '\d+'])]public function inscriptionProspect(Profil $profil = null): Response{if (!$profil instanceof Profil) {throw $this->createNotFoundException("Le profil sélectionné est introuvable.");}$addProspectForm = $this->createForm(DossierInfosType::class,new Dossier(),['action' => $this->generateUrl("inscription_add_prospect", ['id' => $profil->getId()]),]);return $this->render('front/inscription/prospect/inscriptionProspect.html.twig', ['addProspectForm' => $addProspectForm->createView(),'vueData' => [],]);}#[Route(path: '/{id}/devis', name: 'devis', requirements: ['id' => '\d+'])]public function devisEntreprise(Entreprise $entreprise = null): Response{return $this->render('front/inscription/prospect/devis.html.twig', ['vueData' => ['card' => $entreprise->getCart()],'entreprise' => $entreprise]);}#[Route(path: '/entreprise', name: 'entreprise')]public function inscriptionEntreprise(): Response{$addEntrepriseForm = $this->createForm(EntrepriseInfosType::class,new Entreprise(),['action' => $this->generateUrl("inscription_add_entreprise"),]);return $this->render('front/inscription/prospect/inscriptionEntreprise.html.twig', ['addEntrepriseForm' => $addEntrepriseForm->createView(),'vueData' => [],]);}#[Route(path: '/prospect/redirect', name: 'prospect_redirect', methods: ['POST'])]public function redirectProspect(Request $request): Response{$selectedProfilId = $request->request->get('selectedProfil');$profil = $this->profilService->get((int)$selectedProfilId);if (!$profil) {$this->addFlash('error', 'Le profil sélectionné est introuvable.');return $this->redirectToRoute('inscription_profil');}if ($profil->getId() !== 1) {return $this->redirectToRoute('inscription_prospect_inscription', ['id' => $profil->getId()]);}return $this->redirectToRoute('inscription_entreprise');}/*** @throws NonUniqueResultException*/#[Route(path: '/{id}/add/prospect', name: 'add_prospect', methods: ['POST'])]public function addProspect(Profil $profil, Request $request): Response{$data = $request->request->all("dossier_infos");$events = $data['events']??null;if (empty($data['emailCandidature'])) {return $this->json(["error" => "Le champ 'Email notification' est vide. Vous devez sélectionner un email notification."], 400);}if (empty($data['personalInformations']['civilite'])) {return $this->json(["error" => "Le champ 'Civilité' est vide. Vous devez sélectionner une civilité."], 400);}if (empty($data['personalInformations']['nom'])) {return $this->json(["error" => "Le champ 'Nom' est vide. Vous devez ajouter un nom."], 400);}if (empty($data['personalInformations']['prenom'])) {return $this->json(["error" => "Le champ 'Prenom' est vide. Vous devez ajouter un prenom."], 400);}if (empty($data['personalInformations']['dateNaissance'])) {return $this->json(["error" => "Le champ 'Date de Naissance' est vide. Vous devez ajouter une date de Naissance."], 400);}if (empty($data['personalInformations']['villeNaissance'])) {return $this->json(["error" => "Le champ 'Lieu de Naissance' est vide. Vous devez ajouter un lieu de Naissance."], 400);}if (empty($data['personalInformations']['nationalite'])) {return $this->json(["error" => "Le champ 'Nationalité' est vide. Vous devez ajouter une nationalité."], 400);}if (empty($data['personalInformations']['mobile'])) {return $this->json(["error" => "Le champ 'Tel Mobile' est vide. Vous devez ajouter un Tel Mobile."], 400);}$selectedModules = $data["modules"] ?? null;$dossier = new Dossier();$dossier->setProspectAvailable(true);$dossier->setDossierannexes(new DossierAnnexes())->setAdresse(new Adresse())->setPlanning(new Planning());$typeActif = $this->masterlistelgService->getRepository()->getOneByListeCode('DOSSIER', 'STATUTDOSSIER', TypeActifEnum::PROSPECT->value);$dossier->setTypeActif($typeActif);$form = $this->createForm(DossierInfosType::class, $dossier);$form->handleRequest($request);if ($form->isSubmitted() /*&& $form->isValid()*/) {$dossier->setProfil($profil);$this->dossierService->persist($dossier, true);if (!empty($events)) {$this->inscriptionService->addEvents($events, $dossier);}if(!empty($selectedModules)) {$this->inscriptionService->addModules($selectedModules, $dossier);}$dossier = $this->inscriptionService->initDossierProspect($dossier, $typeActif);$model='email_reception_demande_devis';$data = [ "dossier" => $dossier];try {$this->modelDocumentService->generateEmail($model, $data, $dossier->getEmailCandidature());} catch (TransportExceptionInterface|LoaderError|RuntimeError|SyntaxError $e) {}return $this->json($this->dossierService->serializeInfosGeneralesSection($dossier));}return $this->json('error', 500);}/*** @throws NonUniqueResultException* @throws JsonException*/#[Route(path: '/add/postulant', name: 'add_postulant', methods: ['POST'])]public function addPostulant(Request $request): Response{$data = $request->request->all("dossier_infos");$root = $request->request->all();$isRootPayload = empty($data) && !empty($root);if ($isRootPayload) {$profilCode = $root['profil'] ?? null;if (empty($profilCode)) {return $this->json(["error" => "Le champ 'Profil' est vide. Vous devez sélectionner un profil."], 400);}$profilEntity = $this->profilService->getRepository()->findOneByCode((string) $profilCode);if (!$profilEntity) {return $this->json(["error" => "Le profil sélectionné est introuvable."], 400);}$typeFormationCode = $root['typeformation'] ?? null;if (empty($typeFormationCode)) {return $this->json(["error" => "Le champ 'Type de formation' est vide. Vous devez sélectionner un type de formation."], 400);}$selectedTypeFormationEntity = $this->masterlistelgService->getRepository()->getOneByListeCode('FORMATIONS', 'TYPEFORMATION', (string) $typeFormationCode);if (!$selectedTypeFormationEntity) {return $this->json(["error" => "Le type de formation sélectionné est introuvable."], 400);}$dispositifCode = $root['dispositif'] ?? null;if (empty($dispositifCode)) {return $this->json(["error" => "Le champ 'Dispositif' est vide. Vous devez sélectionner un dispositif."], 400);}$selectedDispositifEntity = $this->masterlistelgService->getRepository()->getOneByListeCode('FORMATIONS', 'TYPEDISPOSITIF', (string) $dispositifCode);if (!$selectedDispositifEntity) {return $this->json(["error" => "Le dispositif sélectionné est introuvable."], 400);}$selectedParcours = $root['parcours'] ?? null;if (empty($selectedParcours) || $selectedParcours === '0') {return $this->json(["error" => "Le champ 'Parcours' est vide. Vous devez sélectionner un parcours."], 400);}$parcoursEntity = null;if (ctype_digit((string) $selectedParcours)) {$parcoursEntity = $this->parcoursService->getRepository()->find((int) $selectedParcours);} else {$sigle = strtoupper(trim((string) $selectedParcours));$parcoursEntity = $this->em->createQueryBuilder()->select('p')->from(Parcours::class, 'p')->andWhere('UPPER(p.sigle) = :sigle')->andWhere('(p.archive = false OR p.archive IS NULL)')->setParameter('sigle', $sigle)->setMaxResults(1)->getQuery()->getOneOrNullResult();}if (!$parcoursEntity) {return $this->json(["error" => "Le parcours sélectionné est introuvable."], 400);}$selectedSessions = $root['session'] ?? null;$selectedSessionsEntity = null;if (!empty($selectedSessions) && ctype_digit((string) $selectedSessions)) {$selectedSessionsEntity = $this->sessionParcoursService->getRepository()->find((int) $selectedSessions);}$data = ['profil' => $profilEntity->getId(),'typeFormation' => $selectedTypeFormationEntity->getId(),'dispositif' => $selectedDispositifEntity->getId(),'parcours' => $parcoursEntity->getId(),'session' => $selectedSessionsEntity?->getId(),'emailCandidature' => $root['emailCandidature'] ?? null,'personalInformations' => ['nom' => $root['nom'] ?? null,'prenom' => $root['prenom'] ?? null,'mobile' => $root['mobile'] ?? null,'dateNaissance' => $root['dateNaissance'] ?? null,'villeNaissance' => $root['villeNaissance'] ?? null,],];}if (empty($data['profil'])) {return $this->json(["error" => "Le champ 'Profil' est vide. Vous devez sélectionner un profil."], 400);}if (empty($data['typeFormation'])) {return $this->json(["error" => "Le champ 'Type de formation' est vide. Vous devez sélectionner un type de formation."], 400);}if (empty($data['dispositif'])) {return $this->json(["error" => "Le champ 'Dispositif' est vide. Vous devez sélectionner un dispositif."], 400);}$selectedParcours = ($data["parcours"] == "0") ? null : $data["parcours"];if (empty($selectedParcours)) {return $this->json(["error" => "Le champ 'Parcours' est vide. Vous devez sélectionner un parcours."], 400);}$selectedTypeFormation = $data["typeFormation"];$selectedDispositif = $data["dispositif"];$selectedParcours = ($data["parcours"] == "0") ? null : $data["parcours"];$selectedSessions = $data['session'] ?? null;$parcoursEntity = null;if (!empty($selectedParcours)) {if (ctype_digit((string) $selectedParcours)) {$parcoursEntity = $this->parcoursService->getRepository()->find((int) $selectedParcours);} else {$sigle = strtoupper(trim((string) $selectedParcours));$parcoursEntity = $this->em->createQueryBuilder()->select('p')->from(Parcours::class, 'p')->andWhere('UPPER(p.sigle) = :sigle')->andWhere('(p.archive = false OR p.archive IS NULL)')->setParameter('sigle', $sigle)->setMaxResults(1)->getQuery()->getOneOrNullResult();}}$dossier = new Dossier();$dossier->setPostulantAvailable(true);$dossier->setDossierannexes(new DossierAnnexes())->setAdresse(new Adresse())->setPlanning(new Planning());$typeActif = $this->masterlistelgService->getRepository()->getOneByListeCode('DOSSIER', 'STATUTDOSSIER', TypeActifEnum::POSTULANT->value);$dossier->setTypeActif($typeActif);$selectedDispositifEntity = $this->masterlistelgService->getRepository()->find($selectedDispositif);$selectedTypeFormationEntity = $this->masterlistelgService->getRepository()->find($selectedTypeFormation);$selectedSessionsEntity = $selectedSessions ? $this->sessionParcoursService->getRepository()->find($selectedSessions) : null;$form = $this->createForm(DossierInfosType::class, $dossier, ['selectedDispositif' => $selectedDispositifEntity,'selectedTypeFormation' => $selectedTypeFormationEntity,'selectedParcours' => $parcoursEntity,'selectedSessions' => $selectedSessionsEntity,]);if ($isRootPayload) {$form->submit($data);} else {$form->handleRequest($request);}if ($form->isSubmitted() /*&& $form->isValid()*/) {$statutDossier = $this->masterlistelgService->getRepository()->getOneByListeCode('DOSSIER', 'STATE', 'nontraite');$dossier->setState($statutDossier);$this->dossierService->persist($dossier, true);$historiqueDossier = new HistoriqueDossier();$historiqueDossier->setDossier($dossier)->setType("statut")->setStatut($typeActif);$model='email_reception_candidature';$data = [ "dossier" => $dossier];try {$email = (string) ($dossier->getEmailCandidature() ?? '');if ($email !== '' && !filter_var($email, FILTER_VALIDATE_EMAIL)) {return $this->json(["error" => "Email \"{$email}\" invalide."], 400);}$this->modelDocumentService->generateEmail($model, $data, $email);} catch (TransportExceptionInterface|RfcComplianceException|LoaderError|RuntimeError|SyntaxError $e) {}$lead = $this->dossierToLeadService->dossier_to_lead($dossier);if ($parcoursEntity) {$defaultEmploye = $this->resolveDefaultEmployeForParcours($parcoursEntity);if ($defaultEmploye) {$lead->setEmploye($defaultEmploye);$this->em->flush();}}return $this->json($this->dossierService->serializeInfosGeneralesSection($dossier));}return $this->json('error', 500);}#[Route(path: '/add/entreprise', name: 'add_entreprise', methods: ['POST'])]public function addEntreprise(Request $request): Response{$entreprise = new Entreprise();$contact = new Contact();$entreprise->setDelegataire(false);$data = $request->request->all('entreprise_infos');if (empty($data['raisonSociale'])) {return $this->json(["error" => "Le champ 'Raison Sociale' est vide. Vous devez ajouter un raison sociale."], 400);}if (empty($data['email'])) {return $this->json(["error" => "Le champ 'Email' est vide. Vous devez ajouter un email."], 400);}if (empty($data['mobile'])) {return $this->json(["error" => "Le champ 'Téléphone mobile' est vide. Vous devez ajouter un mobile."], 400);}if (empty($data['siren'])) {return $this->json(["error" => "Le champ 'Siret' est vide. Vous devez ajouter une siren."], 400);}if (empty($data['numtva'])) {return $this->json(["error" => "Le champ 'N° TVA' est vide. Vous devez ajouter un N° TVA."], 400);}if (empty($data['naf'])) {return $this->json(["error" => "Le champ 'NAF' est vide. Vous devez sélectionner un NAF."], 400);}if (empty($data['modules'])) {return $this->json(["error" => "Le champ 'modules' est vide. Vous devez sélectionner un module."], 400);}$contactData = $data['contact'] ?? null;if (empty($contactData['personalInformations']['civilite'])) {return $this->json(["error" => "Le champ 'Civilité' est vide. Vous devez sélectionner une civilité."], 400);}if (empty($contactData['personalInformations']['nom'])) {return $this->json(["error" => "Le champ 'Nom' est vide. Vous devez sélectionner un nom."], 400);}if (empty($contactData['personalInformations']['prenom'])) {return $this->json(["error" => "Le champ 'Prenom' est vide. Vous devez sélectionner un prenom."], 400);}if (empty($contactData['email'])) {return $this->json(["error" => "Le champ 'Email Contact' est vide. Vous devez ajouter un email."], 400);}$selectedModules = ($data["modules"] == "0") ? null : $data["modules"];$contact = $this->inscriptionService->addContact($contactData, $contact);$form = $this->createForm(EntrepriseInfosType::class, $entreprise);$form->handleRequest($request);if ($form->isSubmitted() /*&& $form->isValid()*/) {$user = $this->userService->getRepository()->findOneBy(['email' => $entreprise->getEmail()]);if ($user) {return $this->json(['error' => 'cette adresse email est déja prise'], 400);}$this->inscriptionService->addModulesEntreprise($entreprise, $selectedModules);$this->entrepriseService->persist($entreprise, true);$contact->setTiers($entreprise);$this->entrepriseService->flush();$model='email_reception_candidature_entreprise';$data = [ "entreprise" => $entreprise];try {$this->modelDocumentService->generateEmail($model, $data, $entreprise->getPersonne()->getEmail());} catch (TransportExceptionInterface|LoaderError|RuntimeError|SyntaxError $e) {}return $this->json($this->entrepriseService->serializeInfosGeneralessSection($entreprise));}foreach ($form->getErrors(true) as $error) {if ($error->getOrigin()->getName() === 'email' && $error->getMessage() === 'cette adresse email est déja prise') {return $this->json(['error' => 'cette adresse email est déja prise'], 400);}}return $this->json(["error" => true], 200);}}