PluginProbe
AcyMailing – An Ultimate Newsletter Plugin and Marketing Automation Solution for WordPress / trunk
AcyMailing – An Ultimate Newsletter Plugin and Marketing Automation Solution for WordPress vtrunk
11.0.5 11.0.4 11.0.3 11.0.2 11.0.1 11.0.0 10.11.1 10.11.0 10.10.2 10.10.1 10.10.0 10.9.1 trunk 10.0.0 10.0.1 10.1.0 10.1.1 10.1.2 10.1.3 10.1.4 10.2.0 10.2.1 10.2.2 10.3.0 10.4.0 All 60 releases
acymailing / back / dynamics / elasticemail / plugin.php

plugin.php in AcyMailing – An Ultimate Newsletter Plugin and Marketing Automation Solution for WordPress trunk, at back/dynamics/elasticemail/plugin.php

310 lines 10.9 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 use AcyMailerPhp\Mailer;
4 use AcyMailing\Classes\CampaignClass;
5 use AcyMailing\Classes\MailClass;
6 use AcyMailing\Helpers\MailerHelper;
7 use AcyMailing\Core\AcymPlugin;
8
9 class plgAcymElasticemail extends AcymPlugin
10 {
11 const SENDING_METHOD_ID = 'elasticemail';
12 const SENDING_METHOD_NAME = 'Elastic Email';
13 const SENDING_METHOD_API_URL = 'https://api.elasticemail.com/v4/';
14
15 private $mailClass;
16 private $campaignClass;
17 private $attachmentsFetched = false;
18 private $uploadedAttachments = [];
19
20 public function __construct()
21 {
22 parent::__construct();
23 $this->pluginDescription->name = self::SENDING_METHOD_NAME;
24 }
25
26 public function onAcymGetSendingMethods(&$data, $isMailer = false)
27 {
28 $data['sendingMethods'][self::SENDING_METHOD_ID] = [
29 'name' => $this->pluginDescription->name,
30 'image' => ACYM_IMAGES.'mailers/elasticemail.png',
31 ];
32 }
33
34 public function onAcymGetSendingMethodsHtmlSetting(&$data)
35 {
36 ob_start();
37 ?>
38 <div class="send_settings grid-x cell" id="<?php echo esc_attr(self::SENDING_METHOD_ID); ?>_settings">
39 <div class="cell grid-x acym_vcenter acym__sending__methods__one__settings">
40 <label for="<?php echo esc_attr(self::SENDING_METHOD_ID); ?>_password" class="cell shrink margin-right-1">
41 <?php echo esc_html(acym_translation('ACYM_API_KEY')); ?>
42 </label>
43 <?php
44 $this->getLinks(
45 'https://elasticemail.com/referral-reward?r=7b884a0b-b979-4473-8803-06ae39d76599',
46 'https://elasticemail.com/email-api-pricing?r=7b884a0b-b979-4473-8803-06ae39d76599'
47 );
48 ?>
49 <input id="<?php echo esc_attr(self::SENDING_METHOD_ID); ?>_password"
50 class="cell"
51 type="text"
52 name="config[<?php echo esc_attr(self::SENDING_METHOD_ID); ?>_password]"
53 value="<?php echo esc_attr(str_repeat('*', strlen($this->config->get(self::SENDING_METHOD_ID.'_password')))); ?>">
54 <?php $this->getTestCredentialsSendingMethodButton(self::SENDING_METHOD_ID); ?>
55 </div>
56 </div>
57 <?php
58 $data['sendingMethodsHtmlSettings'][self::SENDING_METHOD_ID] = ob_get_clean();
59 }
60
61 public function onAcymTestCredentialSendingMethod($sendingMethod, $credentials)
62 {
63 if ($sendingMethod !== self::SENDING_METHOD_ID) {
64 return;
65 }
66
67 $response = $this->callApiSendingMethod(
68 self::SENDING_METHOD_API_URL.'files?limit=1',
69 [],
70 $this->getAuthenticationHeaders($credentials),
71 );
72
73 if (!empty($response['error_curl'])) {
74 acym_sendAjaxResponse(acym_translationSprintf('ACYM_ERROR_OCCURRED_WHILE_CALLING_API', $response['error_curl']), [], false);
75 } elseif (!empty($response['Error'])) {
76 $message = $response['Error'] === 'APIKey Expired'
77 ? acym_translation('ACYM_AUTHENTICATION_FAILS_WITH_API_KEY')
78 : acym_translationSprintf(
79 'ACYM_API_RETURN_THIS_ERROR',
80 $response['Error']
81 );
82 acym_sendAjaxResponse($message, [], false);
83 } else {
84 acym_sendAjaxResponse(acym_translation('ACYM_API_KEY_CORRECT'));
85 }
86 }
87
88 public function onAcymSendEmail(
89 array &$response,
90 MailerHelper $mailerHelper,
91 array $to,
92 array $from,
93 array $reply_to,
94 array $bcc = [],
95 array $attachments = [],
96 $sendingMethodListParams = []
97 ): void {
98 // https://elasticemail.com/developers/api-documentation/rest-api#operation/emailsTransactionalPost
99 if ($mailerHelper->externalMailer !== self::SENDING_METHOD_ID) {
100 return;
101 }
102
103 $data = [
104 'recipients' => new stdClass(),
105 'content' => new stdClass(),
106 ];
107
108 $this->handleAddresses($data, $mailerHelper, $from, $reply_to, $to, $bcc);
109 $this->handleEmailContent($data, $mailerHelper);
110 $this->handleAttachments($data, $attachments);
111 $this->handleHeaders($data, $mailerHelper);
112 $this->handleGA($data, $mailerHelper);
113
114 $responseMailer = $this->callApiSendingMethod(
115 self::SENDING_METHOD_API_URL.'emails/transactional',
116 $data,
117 $this->getAuthenticationHeaders(),
118 'POST'
119 );
120
121 if (!empty($responseMailer['Error'])) {
122 $response['error'] = true;
123 $response['message'] = $responseMailer['Error'];
124 } else {
125 $response['error'] = false;
126 }
127 }
128
129 public function onAcymSendingMethodOptions(&$data)
130 {
131 $data['embedImage'][self::SENDING_METHOD_ID] = false;
132 }
133
134 private function handleAddresses(array &$data, MailerHelper $mailerHelper, array $from, array $reply_to, array $to, array $bcc): void
135 {
136 $data['recipients']->to = [$to['email']];
137
138 if (!empty($bcc)) {
139 $data['recipients']->bcc = [$bcc[0][0]];
140 }
141
142 $data['content']->From = empty($from['name']) ? $from['email'] : $from['name'].' <'.$from['email'].'>';
143 $data['content']->ReplyTo = empty($reply_to['name']) ? $reply_to['email'] : $reply_to['name'].' <'.$reply_to['email'].'>';
144
145 $bounceAddress = $this->getBounceAddress($mailerHelper);
146 if (!empty($bounceAddress)) {
147 $data['content']->EnvelopeFrom = $bounceAddress;
148 }
149 }
150
151 private function handleEmailContent(array &$data, MailerHelper $mailerHelper): void
152 {
153 $data['content']->Subject = $mailerHelper->Subject;
154 $data['content']->Body = [
155 (object)[
156 'ContentType' => 'HTML',
157 'Content' => $mailerHelper->Body,
158 'Charset' => 'utf-8',
159 ],
160 ];
161
162 if (!empty($mailerHelper->AltBody)) {
163 $data['content']->Body[] = (object)[
164 'ContentType' => 'PlainText',
165 'Content' => $mailerHelper->AltBody,
166 'Charset' => 'utf-8',
167 ];
168 }
169 }
170
171 private function handleAttachments(array &$data, array $attachments): void
172 {
173 if (empty($attachments)) {
174 return;
175 }
176
177 if (!$this->attachmentsFetched) {
178 $this->attachmentsFetched = true;
179
180 // Uploaded attachments expire after 35 days by default, so 1000 should be more than enough
181 $uploadedAttachments = $this->callApiSendingMethod(
182 self::SENDING_METHOD_API_URL.'files?limit=1000',
183 [],
184 $this->getAuthenticationHeaders()
185 );
186
187 if (empty($uploadedAttachments['Error'])) {
188 foreach ($uploadedAttachments as $oneAttachment) {
189 $this->uploadedAttachments[] = $oneAttachment['FileName'];
190 }
191 }
192 }
193
194 $data['content']->AttachFiles = [];
195 foreach ($attachments as $attachment) {
196 $fileName = $this->cleanFileName($attachment[1]);
197
198 if (!in_array($fileName, $this->uploadedAttachments)) {
199 $uploadedAttachment = $this->callApiSendingMethod(
200 self::SENDING_METHOD_API_URL.'files',
201 [
202 'BinaryContent' => $attachment['contentEncoded'],
203 'Name' => $fileName,
204 'ContentType' => $attachment[4],
205 ],
206 $this->getAuthenticationHeaders(),
207 'POST'
208 );
209
210 if (empty($uploadedAttachment['FileName'])) {
211 continue;
212 }
213
214 $this->uploadedAttachments[] = $fileName;
215 }
216
217 $data['content']->AttachFiles[] = $fileName;
218 }
219 }
220
221 private function handleHeaders(array &$data, MailerHelper $mailerHelper): void
222 {
223 $data['content']->Headers = new stdClass();
224 $data['content']->Headers->Date = Mailer::rfcDate();
225
226 if (empty($mailerHelper->CustomHeader)) {
227 return;
228 }
229
230 foreach ($mailerHelper->CustomHeader as $oneHeader) {
231 $data['content']->Headers->{$oneHeader[0]} = $oneHeader[1];
232 }
233 }
234
235 private function handleGA(array &$data, MailerHelper $mailerHelper): void
236 {
237 $trackingSystem = $this->config->get('trackingsystem', 'acymailing');
238 if (strpos($trackingSystem, 'google') === false || empty($mailerHelper->mailId)) {
239 return;
240 }
241 $data['content']->Utm = new stdClass();
242 $data['content']->Utm->Source = 'newsletter';
243 $data['content']->Utm->Medium = 'email';
244 $data['content']->Utm->Campaign = acym_getAlias($data['content']->Subject);
245
246 if (empty($this->mailClass)) {
247 $this->mailClass = new MailClass();
248 }
249 $campaignId = $this->mailClass->getCampaignIdByMailId($mailerHelper->mailId);
250
251 if (empty($campaignId)) {
252 $data['content']->Utm->Source .= '_'.$mailerHelper->mailId;
253 } else {
254 if (empty($this->campaignClass)) {
255 $this->campaignClass = new CampaignClass();
256 }
257 $campaign = $this->campaignClass->getOneById($campaignId);
258
259 if (empty($campaign)) {
260 return;
261 }
262
263 $data['content']->Utm->Source .= '_'.$campaignId;
264
265 if (!empty($campaign->sending_params['utm_source'])) {
266 $data['content']->Utm->Source = $campaign->sending_params['utm_source'];
267 }
268
269 if (!empty($campaign->sending_params['utm_medium'])) {
270 $data['content']->Utm->Medium = $campaign->sending_params['utm_medium'];
271 }
272
273 if (!empty($campaign->sending_params['utm_campaign'])) {
274 $data['content']->Utm->Campaign = $campaign->sending_params['utm_campaign'];
275 }
276 }
277 }
278
279 private function getAuthenticationHeaders(array $credentials = []): array
280 {
281 if (
282 !isset($credentials[self::SENDING_METHOD_ID.'_password'])
283 || (
284 !empty($credentials[self::SENDING_METHOD_ID.'_password'])
285 && empty(trim($credentials[self::SENDING_METHOD_ID.'_password'], '*'))
286 )
287 ) {
288 return [
289 'X-ElasticEmail-ApiKey: '.$this->config->get(self::SENDING_METHOD_ID.'_password'),
290 'Content-Type: application/json',
291 ];
292 }
293
294 return [
295 'X-ElasticEmail-ApiKey: '.$credentials[self::SENDING_METHOD_ID.'_password'],
296 'Content-Type: application/json',
297 ];
298 }
299
300 private function cleanFileName(string $fileName): string
301 {
302 // Replace accents with their non-accented equivalent
303 if (function_exists('iconv')) {
304 $fileName = iconv('UTF-8', 'ASCII//TRANSLIT', $fileName);
305 }
306
307 return preg_replace('#[^a-z0-9\.\-\_]#i', '_', $fileName);
308 }
309 }
310