vendor/shopware/platform/src/Core/Content/MailTemplate/Subscriber/MailSendSubscriber.php line 78

Open in your IDE?
  1. <?php declare(strict_types=1);
  2. namespace Shopware\Core\Content\MailTemplate\Subscriber;
  3. use Psr\Log\LoggerInterface;
  4. use Shopware\Core\Checkout\Document\DocumentService;
  5. use Shopware\Core\Content\Mail\Service\AbstractMailService;
  6. use Shopware\Core\Content\MailTemplate\Event\MailSendSubscriberBridgeEvent;
  7. use Shopware\Core\Content\MailTemplate\Exception\MailEventConfigurationException;
  8. use Shopware\Core\Content\MailTemplate\Exception\SalesChannelNotFoundException;
  9. use Shopware\Core\Content\MailTemplate\MailTemplateActions;
  10. use Shopware\Core\Content\MailTemplate\MailTemplateEntity;
  11. use Shopware\Core\Content\Media\MediaService;
  12. use Shopware\Core\Framework\Context;
  13. use Shopware\Core\Framework\DataAbstractionLayer\EntityRepositoryInterface;
  14. use Shopware\Core\Framework\DataAbstractionLayer\Exception\InconsistentCriteriaIdsException;
  15. use Shopware\Core\Framework\DataAbstractionLayer\Search\Criteria;
  16. use Shopware\Core\Framework\Event\BusinessEvent;
  17. use Shopware\Core\Framework\Event\EventData\EventDataType;
  18. use Shopware\Core\Framework\Event\MailActionInterface;
  19. use Shopware\Core\Framework\Validation\DataBag\DataBag;
  20. use Symfony\Component\EventDispatcher\EventSubscriberInterface;
  21. use Symfony\Contracts\EventDispatcher\EventDispatcherInterface;
  22. class MailSendSubscriber implements EventSubscriberInterface
  23. {
  24.     public const ACTION_NAME MailTemplateActions::MAIL_TEMPLATE_MAIL_SEND_ACTION;
  25.     public const MAIL_CONFIG_EXTENSION 'mail-attachments';
  26.     private EntityRepositoryInterface $mailTemplateRepository;
  27.     private MediaService $mediaService;
  28.     private EntityRepositoryInterface $mediaRepository;
  29.     private DocumentService $documentService;
  30.     private EntityRepositoryInterface $documentRepository;
  31.     private LoggerInterface $logger;
  32.     private AbstractMailService $emailService;
  33.     private EventDispatcherInterface $eventDispatcher;
  34.     public function __construct(
  35.         AbstractMailService $emailService,
  36.         EntityRepositoryInterface $mailTemplateRepository,
  37.         MediaService $mediaService,
  38.         EntityRepositoryInterface $mediaRepository,
  39.         EntityRepositoryInterface $documentRepository,
  40.         DocumentService $documentService,
  41.         LoggerInterface $logger,
  42.         EventDispatcherInterface $eventDispatcher
  43.     ) {
  44.         $this->mailTemplateRepository $mailTemplateRepository;
  45.         $this->mediaService $mediaService;
  46.         $this->mediaRepository $mediaRepository;
  47.         $this->documentRepository $documentRepository;
  48.         $this->documentService $documentService;
  49.         $this->logger $logger;
  50.         $this->emailService $emailService;
  51.         $this->eventDispatcher $eventDispatcher;
  52.     }
  53.     public static function getSubscribedEvents(): array
  54.     {
  55.         return [
  56.             self::ACTION_NAME => 'sendMail',
  57.         ];
  58.     }
  59.     /**
  60.      * @throws MailEventConfigurationException
  61.      * @throws SalesChannelNotFoundException
  62.      * @throws InconsistentCriteriaIdsException
  63.      */
  64.     public function sendMail(BusinessEvent $event): void
  65.     {
  66.         $mailEvent $event->getEvent();
  67.         $extension $event->getContext()->getExtension(self::MAIL_CONFIG_EXTENSION);
  68.         if (!$extension instanceof MailSendSubscriberConfig) {
  69.             $extension = new MailSendSubscriberConfig(false, [], []);
  70.         }
  71.         if ($extension->skip()) {
  72.             return;
  73.         }
  74.         if (!$mailEvent instanceof MailActionInterface) {
  75.             throw new MailEventConfigurationException('Not a instance of MailActionInterface', \get_class($mailEvent));
  76.         }
  77.         $config $event->getConfig();
  78.         if (!isset($config['mail_template_id'])) {
  79.             return;
  80.         }
  81.         $mailTemplate $this->getMailTemplate($config['mail_template_id'], $event->getContext());
  82.         if ($mailTemplate === null) {
  83.             return;
  84.         }
  85.         $data = new DataBag();
  86.         $recipients $mailEvent->getMailStruct()->getRecipients();
  87.         if (empty($recipients) && isset($config['recipients'])) {
  88.             $recipients $config['recipients'];
  89.         }
  90.         $data->set('recipients'$recipients);
  91.         $data->set('senderName'$mailTemplate->getTranslation('senderName'));
  92.         $data->set('salesChannelId'$mailEvent->getSalesChannelId());
  93.         $data->set('templateId'$mailTemplate->getId());
  94.         $data->set('customFields'$mailTemplate->getCustomFields());
  95.         $data->set('contentHtml'$mailTemplate->getTranslation('contentHtml'));
  96.         $data->set('contentPlain'$mailTemplate->getTranslation('contentPlain'));
  97.         $data->set('subject'$mailTemplate->getTranslation('subject'));
  98.         $data->set('mediaIds', []);
  99.         $attachments $this->buildAttachments($event$mailTemplate$extension);
  100.         if (!empty($attachments)) {
  101.             $data->set('binAttachments'$attachments);
  102.         }
  103.         $this->eventDispatcher->dispatch(new MailSendSubscriberBridgeEvent($data$mailTemplate$event));
  104.         try {
  105.             $this->emailService->send(
  106.                 $data->all(),
  107.                 $event->getContext(),
  108.                 $this->getTemplateData($mailEvent)
  109.             );
  110.             $writes array_map(static function ($id) {
  111.                 return ['id' => $id'sent' => true];
  112.             }, $extension->getDocumentIds());
  113.             if (!empty($writes)) {
  114.                 $this->documentRepository->update($writes$event->getContext());
  115.             }
  116.         } catch (\Exception $e) {
  117.             $this->logger->error(
  118.                 "Could not send mail:\n"
  119.                 $e->getMessage() . "\n"
  120.                 'Error Code:' $e->getCode() . "\n"
  121.                 "Template data: \n"
  122.                 json_encode($data->all()) . "\n"
  123.             );
  124.         }
  125.     }
  126.     private function getMailTemplate(string $idContext $context): ?MailTemplateEntity
  127.     {
  128.         $criteria = new Criteria([$id]);
  129.         $criteria->addAssociation('media.media');
  130.         $criteria->setLimit(1);
  131.         return $this->mailTemplateRepository
  132.             ->search($criteria$context)
  133.             ->first();
  134.     }
  135.     /**
  136.      * @throws MailEventConfigurationException
  137.      */
  138.     private function getTemplateData(MailActionInterface $event): array
  139.     {
  140.         $data = [];
  141.         /* @var EventDataType $item */
  142.         foreach (array_keys($event::getAvailableData()->toArray()) as $key) {
  143.             $getter 'get' ucfirst($key);
  144.             if (method_exists($event$getter)) {
  145.                 $data[$key] = $event->$getter();
  146.             } else {
  147.                 throw new MailEventConfigurationException('Data for ' $key ' not available.', \get_class($event));
  148.             }
  149.         }
  150.         return $data;
  151.     }
  152.     private function buildAttachments(BusinessEvent $eventMailTemplateEntity $mailTemplateMailSendSubscriberConfig $config): array
  153.     {
  154.         $attachments = [];
  155.         if ($mailTemplate->getMedia() !== null) {
  156.             foreach ($mailTemplate->getMedia() as $mailTemplateMedia) {
  157.                 if ($mailTemplateMedia->getMedia() === null) {
  158.                     continue;
  159.                 }
  160.                 if ($mailTemplateMedia->getLanguageId() !== null && $mailTemplateMedia->getLanguageId() !== $event->getContext()->getLanguageId()) {
  161.                     continue;
  162.                 }
  163.                 $attachments[] = $this->mediaService->getAttachment(
  164.                     $mailTemplateMedia->getMedia(),
  165.                     $event->getContext()
  166.                 );
  167.             }
  168.         }
  169.         if (!empty($config->getMediaIds())) {
  170.             $entities $this->mediaRepository->search(new Criteria($config->getMediaIds()), $event->getContext());
  171.             foreach ($entities as $media) {
  172.                 $attachments[] = $this->mediaService->getAttachment($media$event->getContext());
  173.             }
  174.         }
  175.         if (!empty($config->getDocumentIds())) {
  176.             $criteria = new Criteria($config->getDocumentIds());
  177.             $criteria->addAssociation('documentMediaFile');
  178.             $criteria->addAssociation('documentType');
  179.             $entities $this->documentRepository->search($criteria$event->getContext());
  180.             foreach ($entities as $document) {
  181.                 $document $this->documentService->getDocument($document$event->getContext());
  182.                 $attachments[] = [
  183.                     'content' => $document->getFileBlob(),
  184.                     'fileName' => $document->getFilename(),
  185.                     'mimeType' => $document->getContentType(),
  186.                 ];
  187.             }
  188.         }
  189.         return $attachments;
  190.     }
  191. }