diff --git a/docs/developers/email-collector.md b/docs/developers/email-collector.md index 15d05835..fca53827 100644 --- a/docs/developers/email-collector.md +++ b/docs/developers/email-collector.md @@ -29,7 +29,8 @@ For each `MailboxEmail`: 3. it detects a potential ticket to which the email might reply; 4. if it detects a ticket, it checks that the requester can answer to it and that it is not closed; 5. otherwise it checks the requester has the permission to create tickets in the organization and it creates one based on the `Subject` and the `Body` of the email; -6. finally, it deletes the `MailboxEmail` from the database. +6. it saves attachments as `MessageDocument`s; +7. finally, it deletes the `MailboxEmail` from the database. If anything goes wrong during this process, the error is logged in the relevant `MailboxEmail` `lastError` field. diff --git a/src/Entity/MailboxEmail.php b/src/Entity/MailboxEmail.php index 4f0c621d..e9c9067e 100644 --- a/src/Entity/MailboxEmail.php +++ b/src/Entity/MailboxEmail.php @@ -176,6 +176,15 @@ public function getBody(): string } } + /** + * @return PHPIMAP\Attachment[] + */ + public function getAttachments(): array + { + $email = $this->getEmail(); + return $email->getAttachments()->toArray(); + } + public function getDate(): \DateTimeImmutable { $date = $this->getEmail()->getDate()->first(); diff --git a/src/MessageHandler/CreateTicketsFromMailboxEmailsHandler.php b/src/MessageHandler/CreateTicketsFromMailboxEmailsHandler.php index 0adec793..c117eac6 100644 --- a/src/MessageHandler/CreateTicketsFromMailboxEmailsHandler.php +++ b/src/MessageHandler/CreateTicketsFromMailboxEmailsHandler.php @@ -14,12 +14,16 @@ use App\Repository\MailboxRepository; use App\Repository\MailboxEmailRepository; use App\Repository\MessageRepository; +use App\Repository\MessageDocumentRepository; use App\Repository\TicketRepository; use App\Repository\UserRepository; use App\Security\Authentication\UserToken; use App\Security\Encryptor; +use App\Service\MessageDocumentStorage; +use App\Service\MessageDocumentStorageError; use Psr\Log\LoggerInterface; use Symfony\Component\HtmlSanitizer\HtmlSanitizerInterface; +use Symfony\Component\HttpFoundation\File\File; use Symfony\Component\Messenger\Attribute\AsMessageHandler; use Symfony\Component\Messenger\MessageBusInterface; use Symfony\Component\Security\Core\Authorization\AccessDecisionManagerInterface; @@ -31,6 +35,8 @@ class CreateTicketsFromMailboxEmailsHandler public function __construct( private MailboxEmailRepository $mailboxEmailRepository, private MessageRepository $messageRepository, + private MessageDocumentRepository $messageDocumentRepository, + private MessageDocumentStorage $messageDocumentStorage, private TicketRepository $ticketRepository, private UserRepository $userRepository, private AccessDecisionManagerInterface $accessDecisionManager, @@ -119,6 +125,35 @@ public function __invoke(CreateTicketsFromMailboxEmails $message): void $this->ticketRepository->save($ticket, true); $this->messageRepository->save($message, true); + + foreach ($mailboxEmail->getAttachments() as $attachment) { + $tmpPath = sys_get_temp_dir(); + $filename = $attachment->getName(); + $status = $attachment->save($tmpPath, $filename); + + if (!$status) { + $this->logger->warning( + "MailboxEmail {$mailboxEmail->getId()} cannot import {$filename}: can't save in temporary dir" + ); + continue; + } + + $filepath = $tmpPath . '/' . $filename; + $file = new File($filepath, false); + + try { + $messageDocument = $this->messageDocumentStorage->store($file, $filename); + } catch (MessageDocumentStorageError $e) { + $this->logger->warning( + "MailboxEmail {$mailboxEmail->getId()} cannot import {$filename}: {$e->getMessage()}" + ); + continue; + } + + $messageDocument->setMessage($message); + $this->messageDocumentRepository->save($messageDocument, true); + } + $this->mailboxEmailRepository->remove($mailboxEmail, true); $this->bus->dispatch(new SendMessageEmail($message->getId()));