src/Domain/Notification/Subscriber/NotificationEventSubscriber.php line 144

Open in your IDE?
  1. <?php
  2. namespace App\Domain\Notification\Subscriber;
  3. use App\Application\Interfaces\CollectivityRelated;
  4. use App\Domain\Notification\Dictionary\NotificationModuleDictionary;
  5. use App\Domain\Notification\Event\ConformiteTraitementNeedsAIPDEvent;
  6. use App\Domain\Notification\Event\LateActionEvent;
  7. use App\Domain\Notification\Event\LateRequestEvent;
  8. use App\Domain\Notification\Event\LateSurveyEvent;
  9. use App\Domain\Notification\Event\NoLoginEvent;
  10. use App\Domain\Notification\Model\Notification;
  11. use App\Domain\Notification\Model\NotificationUser;
  12. use App\Domain\Notification\Serializer\NotificationNormalizer;
  13. use App\Domain\Registry\Model\ConformiteTraitement\ConformiteTraitement;
  14. use App\Domain\User\Dictionary\UserMoreInfoDictionary;
  15. use App\Domain\User\Model\User;
  16. use App\Domain\User\Repository\User as UserRepository;
  17. use App\Infrastructure\ORM\Notification\Repository\Notification as NotificationRepository;
  18. use App\Infrastructure\ORM\Notification\Repository\NotificationUser as NotificationUserRepository;
  19. use Symfony\Component\EventDispatcher\EventSubscriberInterface;
  20. use Symfony\Component\Serializer\Normalizer\AbstractObjectNormalizer;
  21. use Symfony\Contracts\Translation\TranslatorInterface;
  22. /**
  23.  * This event subscriber creates notification for things that are trigerred by a cron job.
  24.  */
  25. class NotificationEventSubscriber implements EventSubscriberInterface
  26. {
  27.     protected NotificationRepository $notificationRepository;
  28.     protected NotificationUserRepository $notificationUserRepository;
  29.     protected NotificationNormalizer $normalizer;
  30.     protected UserRepository $userRepository;
  31.     protected TranslatorInterface $translator;
  32.     protected string $requestDays;
  33.     protected string $surveyDays;
  34.     public function __construct(
  35.         NotificationRepository $notificationRepository,
  36.         NotificationUserRepository $notificationUserRepository,
  37.         NotificationNormalizer $normalizer,
  38.         UserRepository $userRepository,
  39.         TranslatorInterface $translator,
  40.         string $requestDays,
  41.         string $surveyDays,
  42.     ) {
  43.         $this->notificationRepository     $notificationRepository;
  44.         $this->notificationUserRepository $notificationUserRepository;
  45.         $this->normalizer                 $normalizer;
  46.         $this->userRepository             $userRepository;
  47.         $this->translator                 $translator;
  48.         $this->requestDays                $requestDays;
  49.         $this->surveyDays                 $surveyDays;
  50.     }
  51.     public static function getSubscribedEvents()
  52.     {
  53.         return [
  54.             LateActionEvent::class                    => 'onLateAction',
  55.             LateRequestEvent::class                   => 'onLateRequest',
  56.             NoLoginEvent::class                       => 'onNoLogin',
  57.             LateSurveyEvent::class                    => 'onLateSurvey',
  58.             ConformiteTraitementNeedsAIPDEvent::class => 'onNeedsAIPD',
  59.         ];
  60.     }
  61.     public function onNeedsAIPD(ConformiteTraitementNeedsAIPDEvent $event)
  62.     {
  63.         $conformite $event->getConformiteTraitement();
  64.         $collectivity $conformite->getTraitement()->getCollectivity();
  65.         $existing     $this->notificationRepository->findBy([
  66.             'module'       => 'notification.modules.aipd',
  67.             'collectivity' => $collectivity,
  68.             'action'       => 'notifications.actions.treatment_needs_aipd',
  69.             'name'         => $conformite->__toString(),
  70.         ]);
  71.         if ($existing && count($existing)) {
  72.             return;
  73.         }
  74.         $norm  $this->normalizer->normalize($conformitenullself::normalizerOptions());
  75.         $users $this->userRepository->findNonDpoUsersForCollectivity($collectivity);
  76.         $notification = new Notification();
  77.         $notification->setModule('notification.modules.aipd');
  78.         $notification->setCollectivity($collectivity);
  79.         $notification->setAction('notifications.actions.treatment_needs_aipd');
  80.         $notification->setName($conformite->__toString());
  81.         $notification->setObject((object) $norm);
  82.         $notification->setDpo(true);
  83.         $notification->setSubject('');
  84.         $this->notificationRepository->insert($notification);
  85.         $nus $this->notificationUserRepository->saveUsers($notification$users);
  86.         $notification->setNotificationUsers($nus);
  87.         $this->notificationRepository->update($notification);
  88.         $this->saveEmailNotificationForDPOs($notification$conformite);
  89.     }
  90.     /**
  91.      * Indice de maturité non réalisé depuis plus de...
  92.      *
  93.      * @throws \Symfony\Component\Serializer\Exception\ExceptionInterface
  94.      */
  95.     public function onLateSurvey(LateSurveyEvent $event)
  96.     {
  97.         $survey   $event->getSurvey();
  98.         $existing $this->notificationRepository->findBy([
  99.             'module'       => 'notification.modules.maturity',
  100.             'collectivity' => $survey->getCollectivity(),
  101.             'action'       => 'notifications.actions.late_survey',
  102.             'name'         => $survey->__toString(),
  103.         ]);
  104.         if ($existing && count($existing)) {
  105.             return;
  106.         }
  107.         $norm $this->normalizer->normalize($surveynullself::normalizerOptions());
  108.         $users $this->userRepository->findNonDpoUsersForCollectivity($survey->getCollectivity());
  109.         $notification = new Notification();
  110.         $notification->setModule('notification.modules.maturity');
  111.         $notification->setCollectivity($survey->getCollectivity());
  112.         $notification->setAction('notifications.actions.late_survey');
  113.         $notification->setName($survey->__toString());
  114.         $notification->setObject((object) $norm);
  115.         $notification->setDpo(true);
  116.         $notification->setSubject($this->translator->trans('notifications.subject.late_survey', ['%days%' => $this->surveyDays]));
  117.         $this->notificationRepository->insert($notification);
  118.         $nus $this->notificationUserRepository->saveUsers($notification$users);
  119.         $notification->setNotificationUsers($nus);
  120.         $this->notificationRepository->update($notification);
  121.     }
  122.     /**
  123.      * Action planifiée en retard.
  124.      *
  125.      * @throws \Symfony\Component\Serializer\Exception\ExceptionInterface
  126.      */
  127.     public function onLateAction(LateActionEvent $event)
  128.     {
  129.         $action   $event->getMesurement();
  130.         $existing $this->notificationRepository->findBy([
  131.             'module'       => 'notification.modules.' NotificationModuleDictionary::ACTION_PLAN,
  132.             'collectivity' => $action->getCollectivity(),
  133.             'action'       => 'notifications.actions.late_action',
  134.             'name'         => $action->getName(),
  135.         ]);
  136.         if ($existing && count($existing)) {
  137.             return;
  138.         }
  139.         $norm $this->normalizer->normalize($actionnullself::normalizerOptions());
  140.         $users        $this->userRepository->findNonDpoUsersForCollectivity($action->getCollectivity());
  141.         $notification = new Notification();
  142.         $notification->setModule('notification.modules.' NotificationModuleDictionary::ACTION_PLAN);
  143.         $notification->setCollectivity($action->getCollectivity());
  144.         $notification->setAction('notifications.actions.late_action');
  145.         $notification->setName($action->getName());
  146.         $notification->setObject((object) $norm);
  147.         $notification->setDpo(true);
  148.         $ob   $notification->getObject();
  149.         $date \DateTime::createFromFormat(DATE_ATOM$ob->planificationDate)->format('d/m/Y');
  150.         $notification->setSubject($this->translator->trans('notifications.subject.late_action', ['%date%' => $date]));
  151.         $this->notificationRepository->insert($notification);
  152.         $nus $this->notificationUserRepository->saveUsers($notification$users);
  153.         $notification->setNotificationUsers($nus);
  154.         $this->notificationRepository->update($notification);
  155.         // Send email to référent opérationnel
  156.         $this->saveEmailNotificationForRefOp($notification$action);
  157.     }
  158.     public function onLateRequest(LateRequestEvent $event)
  159.     {
  160.         $request  $event->getRequest();
  161.         $existing $this->notificationRepository->findBy([
  162.             'module'       => 'notification.modules.request',
  163.             'collectivity' => $request->getCollectivity(),
  164.             'action'       => 'notifications.actions.late_request',
  165.             'name'         => $request->__toString(),
  166.         ]);
  167.         if ($existing && count($existing)) {
  168.             return;
  169.         }
  170.         $norm $this->normalizer->normalize($requestnullself::normalizerOptions());
  171.         $users $this->userRepository->findNonDpoUsersForCollectivity($request->getCollectivity());
  172.         $notification = new Notification();
  173.         $notification->setModule('notification.modules.request');
  174.         $notification->setCollectivity($request->getCollectivity());
  175.         $notification->setAction('notifications.actions.late_request');
  176.         $notification->setName($request->__toString());
  177.         $notification->setObject((object) $norm);
  178.         $notification->setDpo(true);
  179.         $notification->setSubject($this->translator->trans('notifications.subject.late_request', ['%days%' => $this->requestDays]));
  180.         $this->notificationRepository->insert($notification);
  181.         $nus $this->notificationUserRepository->saveUsers($notification$users);
  182.         $notification->setNotificationUsers($nus);
  183.         $this->notificationRepository->update($notification);
  184.         // Send email to référent opérationnel and responsable de traitement
  185.         $this->saveEmailNotificationForRefOp($notification$request);
  186.         $this->saveEmailNotificationForRespTrait($notification$request);
  187.     }
  188.     public function onNoLogin(NoLoginEvent $event)
  189.     {
  190.         // Send email to référent opérationnel
  191.         // Add notification for DPO
  192.         $user     $event->getUser();
  193.         $existing $this->notificationRepository->findBy([
  194.             'module'       => 'notification.modules.user',
  195.             'collectivity' => $user->getCollectivity(),
  196.             'action'       => 'notifications.actions.no_login',
  197.             'name'         => $user->getFullName(),
  198.         ]);
  199.         if (count($existing)) {
  200.             return;
  201.         }
  202.         $notification = new Notification();
  203.         $notification->setModule('notification.modules.user');
  204.         $notification->setCollectivity($user->getCollectivity());
  205.         $notification->setAction('notifications.actions.no_login');
  206.         $notification->setName($user->getFullName());
  207.         // $notification->setCreatedBy($user);
  208.         $notification->setObject((object) $this->normalizer->normalize($usernullself::normalizerOptions()));
  209.         $notification->setDpo(true);
  210.         $notification->setSubject($this->translator->trans('notifications.subject.no_login'));
  211.         $this->notificationRepository->insert($notification);
  212.         $this->saveEmailNotificationForRefOp($notification$user);
  213.         // If no NotificationUser, this means the notification is for all DPOs
  214.         // The emails will be sent with notifications:send command to all users that have a unsent NotificationUser with an email address
  215.     }
  216.     private function saveEmailNotificationForRefOp(Notification $notificationCollectivityRelated $object)
  217.     {
  218.         // Get referent operationnels for this collectivity
  219.         $refs $object->getCollectivity()->getUsers()->filter(function (User $u) {
  220.             $mi $u->getMoreInfos();
  221.             return $mi && isset($mi[UserMoreInfoDictionary::MOREINFO_OPERATIONNAL]) && $mi[UserMoreInfoDictionary::MOREINFO_OPERATIONNAL];
  222.         });
  223.         if (=== $refs->count()) {
  224.             // No ref OP, get from collectivity
  225.             if ($object->getCollectivity() && $object->getCollectivity()->getReferent()) {
  226.                 if ($object->getCollectivity()->getReferent()->getNotification()) {
  227.                     $refs = [$object->getCollectivity()->getReferent()->getMail()];
  228.                 }
  229.             }
  230.         }
  231.         // Add notification with email address for the référents
  232.         $this->saveEmailNotifications($notification$refs);
  233.     }
  234.     private function saveEmailNotificationForRespTrait(Notification $notificationCollectivityRelated $object)
  235.     {
  236.         // Get referent operationnels for this collectivity
  237.         $refs $object->getCollectivity()->getUsers()->filter(function (User $u) {
  238.             $mi $u->getMoreInfos();
  239.             return $mi && isset($mi[UserMoreInfoDictionary::MOREINFO_TREATMENT]) && $mi[UserMoreInfoDictionary::MOREINFO_TREATMENT];
  240.         });
  241.         if (=== $refs->count()) {
  242.             // No ref OP, get from collectivity
  243.             if ($object->getCollectivity() && $object->getCollectivity()->getLegalManager()) {
  244.                 if ($object->getCollectivity()->getLegalManager()->getNotification()) {
  245.                     $refs = [$object->getCollectivity()->getLegalManager()->getMail()];
  246.                 }
  247.             }
  248.         }
  249.         $this->saveEmailNotifications($notification$refs);
  250.     }
  251.     private function saveEmailNotificationForDPOs(Notification $notificationConformiteTraitement $object)
  252.     {
  253.         // TODO envoyer à tous les ADMINS + MOREINFO_DPD
  254.         // Get DPOs
  255.         $t    $object->getTraitement();
  256.         $refs $t->getCollectivity()->getUsers()->filter(function (User $u) {
  257.             $mi $u->getMoreInfos();
  258.             return in_array('ROLE_ADMIN'$u->getRoles())
  259.                 || in_array('ROLE_REFERENT'$u->getRoles())
  260.                 || ($mi && isset($mi[UserMoreInfoDictionary::MOREINFO_DPD]) && $mi[UserMoreInfoDictionary::MOREINFO_DPD]);
  261.         });
  262.         // Also get DPOs from collectivity
  263.         if ($t->getCollectivity() && $t->getCollectivity()->getDpo()) {
  264.             if ($t->getCollectivity()->getDpo()->getNotification()) {
  265.                 $refs[] = $t->getCollectivity()->getDpo()->getMail();
  266.             }
  267.         }
  268.         $this->saveEmailNotifications($notification$refs);
  269.     }
  270.     private function saveEmailNotifications(Notification $notification$refs)
  271.     {
  272.         // Add notification with email address for the référents
  273.         foreach ($refs as $ref) {
  274.             $nu = new NotificationUser();
  275.             if (is_object($ref) && User::class === get_class($ref)) {
  276.                 $nu->setMail($ref->getEmail());
  277.                 $nu->setUser($ref);
  278.             } elseif (method_exists($ref'getEmail')) {
  279.                 $nu->setMail($ref->getEmail());
  280.             } elseif (str_contains((string) $ref'@')) {
  281.                 // Only add it if it contains an '@'
  282.                 $nu->setMail((string) $ref);
  283.             }
  284.             $nu->setToken(sha1($notification->getName() . microtime() . $nu->getMail()));
  285.             $nu->setNotification($notification);
  286.             $nu->setActive(false);
  287.             $nu->setSent(false);
  288.             $this->notificationUserRepository->persist($nu);
  289.         }
  290.     }
  291.     public static function normalizerOptions(): array
  292.     {
  293.         return [
  294.             AbstractObjectNormalizer::ENABLE_MAX_DEPTH           => true,
  295.             AbstractObjectNormalizer::CIRCULAR_REFERENCE_LIMIT   => 1,
  296.             AbstractObjectNormalizer::CIRCULAR_REFERENCE_HANDLER => function ($o) {
  297.                 return NotificationNormalizer::getObjectSimpleValue($o);
  298.             },
  299.             AbstractObjectNormalizer::MAX_DEPTH_HANDLER => function ($o) {
  300.                 if (is_iterable($o)) {
  301.                     $d = [];
  302.                     foreach ($o as $item) {
  303.                         $d[] = NotificationNormalizer::getObjectSimpleValue($item);
  304.                     }
  305.                     return $d;
  306.                 }
  307.                 return NotificationNormalizer::getObjectSimpleValue($o);
  308.             },
  309.         ];
  310.     }
  311. }