Passed
Pull Request — master (#140)
by
unknown
04:07 queued 01:40
created

Replyable::setReplyTo()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 7
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 2
eloc 4
nc 2
nop 0
dl 0
loc 7
rs 10
c 0
b 0
f 0
1
<?php
2
3
namespace Ddomanskyi\LaravelGmail\Traits;
4
5
use Ddomanskyi\LaravelGmail\Services\Message\Mail;
6
use Google_Service_Gmail;
7
use Google_Service_Gmail_Message;
8
use Swift_Attachment;
9
use Swift_Message;
10
use Symfony\Component\HttpFoundation\File\Exception\FileNotFoundException;
11
12
/**
13
 * @property Google_Service_Gmail $service
14
 */
15
trait Replyable
16
{
17
	use HasHeaders;
18
19
	private $swiftMessage;
20
21
	/**
22
	 * Gmail optional parameters
23
	 *
24
	 * @var array
25
	 */
26
	private $parameters = [];
27
28
	/**
29
	 * Text or html message to send
30
	 *
31
	 * @var string
32
	 */
33
	private $message;
34
35
	/**
36
	 * Subject of the email
37
	 *
38
	 * @var string
39
	 */
40
	private $subject;
41
42
	/**
43
	 * Sender's email
44
	 *
45
	 * @var string
46
	 */
47
	private $from;
48
49
	/**
50
	 * Sender's name
51
	 *
52
	 * @var  string
53
	 */
54
	private $nameFrom;
55
56
	/**
57
	 * Email of the recipient
58
	 *
59
	 * @var string|array
60
	 */
61
	private $to;
62
63
	/**
64
	 * Name of the recipient
65
	 *
66
	 * @var string
67
	 */
68
	private $nameTo;
69
70
	/**
71
	 * Single email or array of email for a carbon copy
72
	 *
73
	 * @var array|string
74
	 */
75
	private $cc;
76
77
	/**
78
	 * Name of the recipient
79
	 *
80
	 * @var string
81
	 */
82
	private $nameCc;
83
84
	/**
85
	 * Single email or array of email for a blind carbon copy
86
	 *
87
	 * @var array|string
88
	 */
89
	private $bcc;
90
91
	/**
92
	 * Name of the recipient
93
	 *
94
	 * @var string
95
	 */
96
	private $nameBcc;
97
98
	/**
99
	 * List of attachments
100
	 *
101
	 * @var array
102
	 */
103
	private $attachments = [];
104
105
	private $priority = 2;
106
107
	public function __construct()
108
	{
109
		$this->swiftMessage = new Swift_Message();
110
	}
111
112
	/**
113
	 * Receives the recipient's
114
	 * If multiple recipients will receive the message an array should be used.
115
	 * Example: array('[email protected]', '[email protected]' => 'A name')
116
	 *
117
	 * If $name is passed and the first parameter is a string, this name will be
118
	 * associated with the address.
119
	 *
120
	 * @param  string|array  $to
121
	 *
122
	 * @param  string|null  $name
123
	 *
124
	 * @return Replyable
125
	 */
126
	public function to($to, $name = null)
127
	{
128
		$this->to = $to;
129
		$this->nameTo = $name;
130
131
		return $this;
132
	}
133
134
	public function from($from, $name = null)
135
	{
136
		$this->from = $from;
137
		$this->nameFrom = $name;
138
139
		return $this;
140
	}
141
142
	/**
143
	 * @param  array|string  $cc
144
	 *
145
	 * @param  string|null  $name
146
	 *
147
	 * @return Replyable
148
	 */
149
	public function cc($cc, $name = null)
150
	{
151
		$this->cc = $this->emailList($cc, $name);
152
		$this->nameCc = $name;
153
154
		return $this;
155
	}
156
157
	private function emailList($list, $name = null)
158
	{
159
		if (is_array($list)) {
160
			return $this->convertEmailList($list, $name);
161
		} else {
162
			return $list;
163
		}
164
	}
165
166
	private function convertEmailList($emails, $name = null)
167
	{
168
		$newList = [];
169
		$count = 0;
170
		foreach ($emails as $key => $email) {
171
			$emailName = isset($name[$count]) ? $name[$count] : explode('@', $email)[0];
172
			$newList[$email] = $emailName;
173
			$count = $count + 1;
174
		}
175
176
		return $newList;
177
	}
178
179
	/**
180
	 * @param  array|string  $bcc
181
	 *
182
	 * @param  string|null  $name
183
	 *
184
	 * @return Replyable
185
	 */
186
	public function bcc($bcc, $name = null)
187
	{
188
		$this->bcc = $this->emailList($bcc, $name);
189
		$this->nameBcc = $name;
190
191
		return $this;
192
	}
193
194
	/**
195
	 * @param  string  $subject
196
	 *
197
	 * @return Replyable
198
	 */
199
	public function subject($subject)
200
	{
201
		$this->subject = $subject;
202
203
		return $this;
204
	}
205
206
	/**
207
	 * @param  string  $view
208
	 * @param  array  $data
209
	 * @param  array  $mergeData
210
	 *
211
	 * @return Replyable
212
	 * @throws \Throwable
213
	 */
214
	public function view($view, $data = [], $mergeData = [])
215
	{
216
		$this->message = view($view, $data, $mergeData)->render();
0 ignored issues
show
Documentation Bug introduced by
It seems like view($view, $data, $mergeData)->render() can also be of type array. However, the property $message is declared as type string. Maybe add an additional type check?

Our type inference engine has found a suspicous assignment of a value to a property. This check raises an issue when a value that can be of a mixed type is assigned to a property that is type hinted more strictly.

For example, imagine you have a variable $accountId that can either hold an Id object or false (if there is no account id yet). Your code now assigns that value to the id property of an instance of the Account class. This class holds a proper account, so the id value must no longer be false.

Either this assignment is in error or a type check should be added for that assignment.

class Id
{
    public $id;

    public function __construct($id)
    {
        $this->id = $id;
    }

}

class Account
{
    /** @var  Id $id */
    public $id;
}

$account_id = false;

if (starsAreRight()) {
    $account_id = new Id(42);
}

$account = new Account();
if ($account instanceof Id)
{
    $account->id = $account_id;
}
Loading history...
217
218
		return $this;
219
	}
220
221
	/**
222
	 * @param  string  $message
223
	 *
224
	 * @return Replyable
225
	 */
226
	public function message($message)
227
	{
228
		$this->message = $message;
229
230
		return $this;
231
	}
232
233
	/**
234
	 * Attaches new file to the email from the Storage folder
235
	 *
236
	 * @param  array  $files  comma separated of files
237
	 *
238
	 * @return Replyable
239
	 * @throws \Exception
240
	 */
241
	public function attach(...$files)
242
	{
243
244
		foreach ($files as $file) {
245
246
			if (!file_exists($file)) {
247
				throw new FileNotFoundException($file);
248
			}
249
250
			array_push($this->attachments, $file);
251
		}
252
253
		return $this;
254
	}
255
256
	/**
257
	 * The value is an integer where 1 is the highest priority and 5 is the lowest.
258
	 *
259
	 * @param  int  $priority
260
	 *
261
	 * @return Replyable
262
	 */
263
	public function priority($priority)
264
	{
265
		$this->priority = $priority;
266
267
		return $this;
268
	}
269
270
	/**
271
	 * @param  array  $parameters
272
	 *
273
	 * @return Replyable
274
	 */
275
	public function optionalParameters(array $parameters)
276
	{
277
		$this->parameters = $parameters;
278
279
		return $this;
280
	}
281
282
	/**
283
	 * Reply to a specific email
284
	 *
285
	 * @return Mail
286
	 * @throws \Exception
287
	 */
288
	public function reply()
289
	{
290
		if (!$this->getId()) {
291
			throw new \Exception('This is a new email. Use send().');
292
		}
293
294
		$this->setReplyThread();
295
		$this->setReplySubject();
296
		$this->setReplyTo();
297
		$this->setReplyFrom();
298
		$body = $this->getMessageBody();
299
		$body->setThreadId($this->getThreadId());
300
301
		return new Mail($this->service->users_messages->send('me', $body, $this->parameters));
302
	}
303
304
	public abstract function getId();
305
306
	private function setReplyThread()
307
	{
308
		$threadId = $this->getThreadId();
309
		if ($threadId) {
310
			$this->setHeader('In-Reply-To', $this->getHeader('In-Reply-To'));
311
			$this->setHeader('References', $this->getHeader('References'));
312
			$this->setHeader('Message-ID', $this->getHeader('Message-ID'));
313
		}
314
	}
315
316
	public abstract function getThreadId();
317
318
	/**
319
	 * Add a header to the email
320
	 *
321
	 * @param  string  $header
322
	 * @param  string  $value
323
	 */
324
	public function setHeader($header, $value)
325
	{
326
		$headers = $this->swiftMessage->getHeaders();
327
328
		$headers->addTextHeader($header, $value);
329
330
	}
331
332
	private function setReplySubject()
333
	{
334
		if (!$this->subject) {
335
			$this->subject = $this->getSubject();
336
		}
337
	}
338
339
	private function setReplyTo()
340
	{
341
		if (!$this->to) {
342
			$replyTo = $this->getReplyTo();
343
344
			$this->to = $replyTo['email'];
345
			$this->nameTo = $replyTo['name'];
346
		}
347
	}
348
349
	private function setReplyFrom()
350
	{
351
		if (!$this->from) {
352
			$this->from = $this->getUser();
353
			if(!$this->from) {
354
				throw new \Exception('Reply from is not defined');
355
			}
356
		}
357
	}
358
359
	public abstract function getSubject();
360
361
	public abstract function getReplyTo();
362
363
	public abstract function getUser();
364
365
	/**
366
	 * @return Google_Service_Gmail_Message
367
	 */
368
	private function getMessageBody()
369
	{
370
		$body = new Google_Service_Gmail_Message();
371
372
		$this->swiftMessage
373
			->setSubject($this->subject)
374
			->setFrom($this->from, $this->nameFrom)
375
			->setTo($this->to, $this->nameTo)
376
			->setCc($this->cc, $this->nameCc)
377
			->setBcc($this->bcc, $this->nameBcc)
378
			->setBody($this->message, 'text/html')
379
			->setPriority($this->priority);
380
381
		foreach ($this->attachments as $file) {
382
			$this->swiftMessage
383
				->attach(Swift_Attachment::fromPath($file));
384
		}
385
386
		$body->setRaw($this->base64_encode($this->swiftMessage->toString()));
387
388
		return $body;
389
	}
390
391
	private function base64_encode($data)
392
	{
393
		return rtrim(strtr(base64_encode($data), ['+' => '-', '/' => '_']), '=');
394
	}
395
396
	/**
397
	 * Sends a new email
398
	 *
399
	 * @return self|Mail
400
	 */
401
	public function send()
402
	{
403
		$body = $this->getMessageBody();
404
405
		$this->setMessage($this->service->users_messages->send('me', $body, $this->parameters));
406
407
		return $this;
408
	}
409
410
	protected abstract function setMessage($message);
411
}
412