Passed
Push — noreply ( b9bebf )
by Angel Fernando Quiroz
13:27
created

MailHelper   A

Complexity

Total Complexity 25

Size/Duplication

Total Lines 145
Duplicated Lines 0 %

Importance

Changes 0
Metric Value
eloc 66
dl 0
loc 145
rs 10
c 0
b 0
f 0
wmc 25

3 Methods

Rating   Name   Duplication   Size   Complexity  
F send() 0 95 17
B setNoreplyAndFromAddress() 0 38 7
A __construct() 0 7 1
1
<?php
2
3
/* For licensing terms, see /license.txt */
4
5
declare(strict_types=1);
6
7
namespace Chamilo\CoreBundle\Helpers;
8
9
use Chamilo\CoreBundle\Settings\SettingsManager;
10
use Exception;
11
use Notification;
12
use Symfony\Bridge\Twig\Mime\TemplatedEmail;
13
use Symfony\Component\Mailer\Exception\TransportExceptionInterface;
14
use Symfony\Component\Mailer\MailerInterface;
15
use Symfony\Component\Mime\Address;
16
use Symfony\Component\Mime\BodyRendererInterface;
17
use Symfony\Component\Mime\Part\DataPart;
18
use Symfony\Component\Validator\Constraints as Assert;
19
use Symfony\Component\Validator\Validator\ValidatorInterface;
20
21
final class MailHelper
22
{
23
    public function __construct(
24
        private readonly MailerInterface $mailer,
25
        private readonly BodyRendererInterface $bodyRenderer,
26
        private readonly ThemeHelper $themeHelper,
27
        private readonly ValidatorInterface $validator,
28
        private readonly SettingsManager $settingsManager,
29
    ) {}
30
31
    private function setNoreplyAndFromAddress(
32
        TemplatedEmail $email,
33
        array $sender,
34
        array $replyToAddress = []
35
    ): void {
36
        $emailConstraint = new Assert\Email();
37
38
        // Default values
39
        $notification = new Notification();
40
        $defaultSenderName = $notification->getDefaultPlatformSenderName();
41
        $defaultSenderEmail = $notification->getDefaultPlatformSenderEmail();
42
43
        // If the parameter is set, don't use the admin.
44
        $senderName = !empty($sender['name']) ? $sender['name'] : $defaultSenderName;
45
        $senderEmail = !empty($sender['email']) ? $sender['email'] : $defaultSenderEmail;
46
47
        // Send errors to the platform admin
48
        $adminEmail = $this->settingsManager->getSetting('admin.administrator_email');
49
50
        $adminEmailValidation = $this->validator->validate($adminEmail, $emailConstraint);
51
52
        if (!empty($adminEmail) && 0 === $adminEmailValidation->count()) {
53
            $email
54
                ->getHeaders()
55
                ->addIdHeader('Errors-To', $adminEmail)
56
            ;
57
        }
58
59
        // Reply to first
60
        if (!empty($replyToAddress)) {
61
            $replyToEmailValidation = $this->validator->validate($replyToAddress['mail'], $emailConstraint);
62
63
            if (0 === $replyToEmailValidation->count()) {
64
                $email->addReplyTo(new Address($replyToAddress['mail'], $replyToAddress['name']));
65
            }
66
        }
67
68
        $email->from(new Address($senderEmail, $senderName));
69
    }
70
71
    public function send(
72
        string $recipientName,
73
        string $recipientEmail,
74
        string $subject,
75
        string $body,
76
        ?string $senderName = null,
77
        ?string $senderEmail = null,
78
        array $extra_headers = [],
79
        array $data_file = [],
80
        bool $embeddedImage = false,
81
        array $additionalParameters = [],
82
        ?string $sendErrorTo = null,
83
    ): bool {
84
        if (!api_valid_email($recipientEmail)) {
85
            return false;
86
        }
87
88
        $templatedEmail = new TemplatedEmail();
89
90
        $this->setNoreplyAndFromAddress(
91
            $templatedEmail,
92
            ['name' => $senderName, 'email' => $senderEmail],
93
            !empty($extra_headers['reply_to']) ? $extra_headers['reply_to'] : []
94
        );
95
96
        if ($sendErrorTo) {
97
            $templatedEmail
98
                ->getHeaders()
99
                ->addIdHeader('Errors-To', $sendErrorTo)
100
            ;
101
        }
102
103
        // Reply to first
104
        $replyToName = '';
105
        $replyToEmail = '';
106
        if (isset($extra_headers['reply_to'])) {
107
            $replyToEmail = $extra_headers['reply_to']['mail'];
108
            $replyToName = $extra_headers['reply_to']['name'];
109
        }
110
111
        try {
112
            $templatedEmail->subject($subject);
113
114
            $list = api_get_setting('announcement.send_all_emails_to', true);
115
116
            if (!empty($list) && isset($list['emails'])) {
117
                foreach ($list['emails'] as $email) {
118
                    $templatedEmail->cc($email);
119
                }
120
            }
121
122
            // Attachment
123
            if (!empty($data_file)) {
124
                foreach ($data_file as $file_attach) {
125
                    if (!empty($file_attach['path']) && !empty($file_attach['filename'])) {
126
                        $templatedEmail->attachFromPath($file_attach['path'], $file_attach['filename']);
127
                    }
128
129
                    if (!empty($file_attach['stream']) && !empty($file_attach['filename'])) {
130
                        $templatedEmail->addPart(new DataPart($file_attach['stream'], $file_attach['filename']));
131
                    }
132
                }
133
            }
134
135
            $automaticEmailText = '<br />'.get_lang('This is an automatic email message. Please do not reply to it.');
136
137
            $params = [
138
                'mail_header_style' => api_get_setting('mail.mail_header_style'),
139
                'mail_content_style' => api_get_setting('mail.mail_content_style'),
140
                'link' => $additionalParameters['link'] ?? '',
141
                'automatic_email_text' => $automaticEmailText,
142
                'content' => $body,
143
            ];
144
145
            if (!empty($recipientEmail)) {
146
                $templatedEmail->to(new Address($recipientEmail, $recipientName));
147
            }
148
149
            if (!empty($replyToEmail)) {
150
                $templatedEmail->replyTo(new Address($replyToEmail, $replyToName));
151
            }
152
153
            $templatedEmail
154
                ->htmlTemplate('@ChamiloCore/Mailer/Default/default.html.twig')
155
                ->context($params)
156
            ;
157
158
            $this->bodyRenderer->render($templatedEmail);
159
            $this->mailer->send($templatedEmail);
160
161
            return true;
162
        } catch (Exception|TransportExceptionInterface $e) {
163
            error_log($e->getMessage());
164
165
            return false;
166
        }
167
    }
168
}
169