pictcode / lib / Cake / Controller / Component / EmailComponent.php @ master
履歴 | 表示 | アノテート | ダウンロード (10.505 KB)
1 |
<?php
|
---|---|
2 |
/**
|
3 |
* Email Component
|
4 |
*
|
5 |
* CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
|
6 |
* Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
|
7 |
*
|
8 |
* Licensed under The MIT License
|
9 |
* For full copyright and license information, please see the LICENSE.txt
|
10 |
* Redistributions of files must retain the above copyright notice.
|
11 |
*
|
12 |
* @copyright Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
|
13 |
* @link http://cakephp.org CakePHP(tm) Project
|
14 |
* @package Cake.Controller.Component
|
15 |
* @since CakePHP(tm) v 1.2.0.3467
|
16 |
* @license http://www.opensource.org/licenses/mit-license.php MIT License
|
17 |
*/
|
18 |
|
19 |
App::uses('Component', 'Controller'); |
20 |
App::uses('Multibyte', 'I18n'); |
21 |
App::uses('CakeEmail', 'Network/Email'); |
22 |
|
23 |
/**
|
24 |
* EmailComponent
|
25 |
*
|
26 |
* This component is used for handling Internet Message Format based
|
27 |
* based on the standard outlined in http://www.rfc-editor.org/rfc/rfc2822.txt
|
28 |
*
|
29 |
* @package Cake.Controller.Component
|
30 |
* @link http://book.cakephp.org/2.0/en/core-libraries/components/email.html
|
31 |
* @link http://book.cakephp.org/2.0/en/core-utility-libraries/email.html
|
32 |
* @deprecated 3.0.0 Will be removed in 3.0. Use Network/CakeEmail instead
|
33 |
*/
|
34 |
class EmailComponent extends Component { |
35 |
|
36 |
/**
|
37 |
* Recipient of the email
|
38 |
*
|
39 |
* @var string
|
40 |
*/
|
41 |
public $to = null; |
42 |
|
43 |
/**
|
44 |
* The mail which the email is sent from
|
45 |
*
|
46 |
* @var string
|
47 |
*/
|
48 |
public $from = null; |
49 |
|
50 |
/**
|
51 |
* The email the recipient will reply to
|
52 |
*
|
53 |
* @var string
|
54 |
*/
|
55 |
public $replyTo = null; |
56 |
|
57 |
/**
|
58 |
* The read receipt email
|
59 |
*
|
60 |
* @var string
|
61 |
*/
|
62 |
public $readReceipt = null; |
63 |
|
64 |
/**
|
65 |
* The mail that will be used in case of any errors like
|
66 |
* - Remote mailserver down
|
67 |
* - Remote user has exceeded his quota
|
68 |
* - Unknown user
|
69 |
*
|
70 |
* @var string
|
71 |
*/
|
72 |
public $return = null; |
73 |
|
74 |
/**
|
75 |
* Carbon Copy
|
76 |
*
|
77 |
* List of email's that should receive a copy of the email.
|
78 |
* The Recipient WILL be able to see this list
|
79 |
*
|
80 |
* @var array
|
81 |
*/
|
82 |
public $cc = array(); |
83 |
|
84 |
/**
|
85 |
* Blind Carbon Copy
|
86 |
*
|
87 |
* List of email's that should receive a copy of the email.
|
88 |
* The Recipient WILL NOT be able to see this list
|
89 |
*
|
90 |
* @var array
|
91 |
*/
|
92 |
public $bcc = array(); |
93 |
|
94 |
/**
|
95 |
* The date to put in the Date: header. This should be a date
|
96 |
* conforming with the RFC2822 standard. Leave null, to have
|
97 |
* today's date generated.
|
98 |
*
|
99 |
* @var string
|
100 |
*/
|
101 |
public $date = null; |
102 |
|
103 |
/**
|
104 |
* The subject of the email
|
105 |
*
|
106 |
* @var string
|
107 |
*/
|
108 |
public $subject = null; |
109 |
|
110 |
/**
|
111 |
* Associative array of a user defined headers
|
112 |
* Keys will be prefixed 'X-' as per RFC2822 Section 4.7.5
|
113 |
*
|
114 |
* @var array
|
115 |
*/
|
116 |
public $headers = array(); |
117 |
|
118 |
/**
|
119 |
* List of additional headers
|
120 |
*
|
121 |
* These will NOT be used if you are using safemode and mail()
|
122 |
*
|
123 |
* @var string
|
124 |
*/
|
125 |
public $additionalParams = null; |
126 |
|
127 |
/**
|
128 |
* Layout for the View
|
129 |
*
|
130 |
* @var string
|
131 |
*/
|
132 |
public $layout = 'default'; |
133 |
|
134 |
/**
|
135 |
* Template for the view
|
136 |
*
|
137 |
* @var string
|
138 |
*/
|
139 |
public $template = null; |
140 |
|
141 |
/**
|
142 |
* Line feed character(s) to be used when sending using mail() function
|
143 |
* By default PHP_EOL is used.
|
144 |
* RFC2822 requires it to be CRLF but some Unix
|
145 |
* mail transfer agents replace LF by CRLF automatically
|
146 |
* (which leads to doubling CR if CRLF is used).
|
147 |
*
|
148 |
* @var string
|
149 |
*/
|
150 |
public $lineFeed = PHP_EOL; |
151 |
|
152 |
/**
|
153 |
* What format should the email be sent in
|
154 |
*
|
155 |
* Supported formats:
|
156 |
* - text
|
157 |
* - html
|
158 |
* - both
|
159 |
*
|
160 |
* @var string
|
161 |
*/
|
162 |
public $sendAs = 'text'; |
163 |
|
164 |
/**
|
165 |
* What method should the email be sent by
|
166 |
*
|
167 |
* Supported methods:
|
168 |
* - mail
|
169 |
* - smtp
|
170 |
* - debug
|
171 |
*
|
172 |
* @var string
|
173 |
*/
|
174 |
public $delivery = 'mail'; |
175 |
|
176 |
/**
|
177 |
* charset the email is sent in
|
178 |
*
|
179 |
* @var string
|
180 |
*/
|
181 |
public $charset = 'utf-8'; |
182 |
|
183 |
/**
|
184 |
* List of files that should be attached to the email.
|
185 |
*
|
186 |
* Can be both absolute and relative paths
|
187 |
*
|
188 |
* @var array
|
189 |
*/
|
190 |
public $attachments = array(); |
191 |
|
192 |
/**
|
193 |
* What mailer should EmailComponent identify itself as
|
194 |
*
|
195 |
* @var string
|
196 |
*/
|
197 |
public $xMailer = 'CakePHP Email Component'; |
198 |
|
199 |
/**
|
200 |
* The list of paths to search if an attachment isn't absolute
|
201 |
*
|
202 |
* @var array
|
203 |
*/
|
204 |
public $filePaths = array(); |
205 |
|
206 |
/**
|
207 |
* List of options to use for smtp mail method
|
208 |
*
|
209 |
* Options is:
|
210 |
* - port
|
211 |
* - host
|
212 |
* - timeout
|
213 |
* - username
|
214 |
* - password
|
215 |
* - client
|
216 |
*
|
217 |
* @var array
|
218 |
*/
|
219 |
public $smtpOptions = array(); |
220 |
|
221 |
/**
|
222 |
* Contains the rendered plain text message if one was sent.
|
223 |
*
|
224 |
* @var string
|
225 |
*/
|
226 |
public $textMessage = null; |
227 |
|
228 |
/**
|
229 |
* Contains the rendered HTML message if one was sent.
|
230 |
*
|
231 |
* @var string
|
232 |
*/
|
233 |
public $htmlMessage = null; |
234 |
|
235 |
/**
|
236 |
* Whether to generate a Message-ID header for the
|
237 |
* e-mail. True to generate a Message-ID, False to let
|
238 |
* it be handled by sendmail (or similar) or a string
|
239 |
* to completely override the Message-ID.
|
240 |
*
|
241 |
* If you are sending Email from a shell, be sure to set this value. As you
|
242 |
* could encounter delivery issues if you do not.
|
243 |
*
|
244 |
* @var mixed
|
245 |
*/
|
246 |
public $messageId = true; |
247 |
|
248 |
/**
|
249 |
* Controller reference
|
250 |
*
|
251 |
* @var Controller
|
252 |
*/
|
253 |
protected $_controller = null; |
254 |
|
255 |
/**
|
256 |
* Constructor
|
257 |
*
|
258 |
* @param ComponentCollection $collection A ComponentCollection this component can use to lazy load its components
|
259 |
* @param array $settings Array of configuration settings.
|
260 |
*/
|
261 |
public function __construct(ComponentCollection $collection, $settings = array()) { |
262 |
$this->_controller = $collection->getController(); |
263 |
parent::__construct($collection, $settings); |
264 |
} |
265 |
|
266 |
/**
|
267 |
* Initialize component
|
268 |
*
|
269 |
* @param Controller $controller Instantiating controller
|
270 |
* @return void
|
271 |
*/
|
272 |
public function initialize(Controller $controller) { |
273 |
if (Configure::read('App.encoding') !== null) { |
274 |
$this->charset = Configure::read('App.encoding'); |
275 |
} |
276 |
} |
277 |
|
278 |
/**
|
279 |
* Send an email using the specified content, template and layout
|
280 |
*
|
281 |
* @param string|array $content Either an array of text lines, or a string with contents
|
282 |
* If you are rendering a template this variable will be sent to the templates as `$content`
|
283 |
* @param string $template Template to use when sending email
|
284 |
* @param string $layout Layout to use to enclose email body
|
285 |
* @return bool Success
|
286 |
*/
|
287 |
public function send($content = null, $template = null, $layout = null) { |
288 |
$lib = new CakeEmail(); |
289 |
$lib->charset = $this->charset; |
290 |
$lib->headerCharset = $this->charset; |
291 |
|
292 |
$lib->from($this->_formatAddresses((array)$this->from)); |
293 |
if (!empty($this->to)) { |
294 |
$lib->to($this->_formatAddresses((array)$this->to)); |
295 |
} |
296 |
if (!empty($this->cc)) { |
297 |
$lib->cc($this->_formatAddresses((array)$this->cc)); |
298 |
} |
299 |
if (!empty($this->bcc)) { |
300 |
$lib->bcc($this->_formatAddresses((array)$this->bcc)); |
301 |
} |
302 |
if (!empty($this->replyTo)) { |
303 |
$lib->replyTo($this->_formatAddresses((array)$this->replyTo)); |
304 |
} |
305 |
if (!empty($this->return)) { |
306 |
$lib->returnPath($this->_formatAddresses((array)$this->return)); |
307 |
} |
308 |
if (!empty($this->readReceipt)) { |
309 |
$lib->readReceipt($this->_formatAddresses((array)$this->readReceipt)); |
310 |
} |
311 |
|
312 |
$lib->subject($this->subject); |
313 |
$lib->messageID($this->messageId); |
314 |
$lib->helpers($this->_controller->helpers); |
315 |
|
316 |
$headers = array('X-Mailer' => $this->xMailer); |
317 |
foreach ($this->headers as $key => $value) { |
318 |
$headers['X-' . $key] = $value; |
319 |
} |
320 |
if ($this->date) { |
321 |
$headers['Date'] = $this->date; |
322 |
} |
323 |
$lib->setHeaders($headers); |
324 |
|
325 |
if ($template) { |
326 |
$this->template = $template; |
327 |
} |
328 |
if ($layout) { |
329 |
$this->layout = $layout; |
330 |
} |
331 |
$lib->template($this->template, $this->layout)->viewVars($this->_controller->viewVars)->emailFormat($this->sendAs); |
332 |
|
333 |
if (!empty($this->attachments)) { |
334 |
$lib->attachments($this->_formatAttachFiles()); |
335 |
} |
336 |
|
337 |
$lib->transport(ucfirst($this->delivery)); |
338 |
if ($this->delivery === 'mail') { |
339 |
$lib->config(array('eol' => $this->lineFeed, 'additionalParameters' => $this->additionalParams)); |
340 |
} elseif ($this->delivery === 'smtp') { |
341 |
$lib->config($this->smtpOptions); |
342 |
} else {
|
343 |
$lib->config(array()); |
344 |
} |
345 |
|
346 |
$sent = $lib->send($content); |
347 |
|
348 |
$this->htmlMessage = $lib->message(CakeEmail::MESSAGE_HTML); |
349 |
if (empty($this->htmlMessage)) { |
350 |
$this->htmlMessage = null; |
351 |
} |
352 |
$this->textMessage = $lib->message(CakeEmail::MESSAGE_TEXT); |
353 |
if (empty($this->textMessage)) { |
354 |
$this->textMessage = null; |
355 |
} |
356 |
|
357 |
$this->_header = array(); |
358 |
$this->_message = array(); |
359 |
|
360 |
return $sent; |
361 |
} |
362 |
|
363 |
/**
|
364 |
* Reset all EmailComponent internal variables to be able to send out a new email.
|
365 |
*
|
366 |
* @return void
|
367 |
*/
|
368 |
public function reset() { |
369 |
$this->template = null; |
370 |
$this->to = array(); |
371 |
$this->from = null; |
372 |
$this->replyTo = null; |
373 |
$this->return = null; |
374 |
$this->cc = array(); |
375 |
$this->bcc = array(); |
376 |
$this->subject = null; |
377 |
$this->additionalParams = null; |
378 |
$this->date = null; |
379 |
$this->attachments = array(); |
380 |
$this->htmlMessage = null; |
381 |
$this->textMessage = null; |
382 |
$this->messageId = true; |
383 |
$this->delivery = 'mail'; |
384 |
} |
385 |
|
386 |
/**
|
387 |
* Format the attach array
|
388 |
*
|
389 |
* @return array
|
390 |
*/
|
391 |
protected function _formatAttachFiles() { |
392 |
$files = array(); |
393 |
foreach ($this->attachments as $filename => $attachment) { |
394 |
$file = $this->_findFiles($attachment); |
395 |
if (!empty($file)) { |
396 |
if (is_int($filename)) { |
397 |
$filename = basename($file); |
398 |
} |
399 |
$files[$filename] = $file; |
400 |
} |
401 |
} |
402 |
return $files; |
403 |
} |
404 |
|
405 |
/**
|
406 |
* Find the specified attachment in the list of file paths
|
407 |
*
|
408 |
* @param string $attachment Attachment file name to find
|
409 |
* @return string|null Path to located file
|
410 |
*/
|
411 |
protected function _findFiles($attachment) { |
412 |
if (file_exists($attachment)) { |
413 |
return $attachment; |
414 |
} |
415 |
foreach ($this->filePaths as $path) { |
416 |
if (file_exists($path . DS . $attachment)) { |
417 |
$file = $path . DS . $attachment; |
418 |
return $file; |
419 |
} |
420 |
} |
421 |
return null; |
422 |
} |
423 |
|
424 |
/**
|
425 |
* Format addresses to be an array with email as key and alias as value
|
426 |
*
|
427 |
* @param array $addresses Address to format.
|
428 |
* @return array
|
429 |
*/
|
430 |
protected function _formatAddresses($addresses) { |
431 |
$formatted = array(); |
432 |
foreach ($addresses as $address) { |
433 |
if (preg_match('/((.*))?\s?<(.+)>/', $address, $matches) && !empty($matches[2])) { |
434 |
$formatted[$this->_strip($matches[3])] = $matches[2]; |
435 |
} else {
|
436 |
$address = $this->_strip($address); |
437 |
$formatted[$address] = $address; |
438 |
} |
439 |
} |
440 |
return $formatted; |
441 |
} |
442 |
|
443 |
/**
|
444 |
* Remove certain elements (such as bcc:, to:, %0a) from given value.
|
445 |
* Helps prevent header injection / manipulation on user content.
|
446 |
*
|
447 |
* @param string $value Value to strip
|
448 |
* @param bool $message Set to true to indicate main message content
|
449 |
* @return string Stripped value
|
450 |
*/
|
451 |
protected function _strip($value, $message = false) { |
452 |
$search = '%0a|%0d|Content-(?:Type|Transfer-Encoding)\:'; |
453 |
$search .= '|charset\=|mime-version\:|multipart/mixed|(?:[^a-z]to|b?cc)\:.*'; |
454 |
|
455 |
if ($message !== true) { |
456 |
$search .= '|\r|\n'; |
457 |
} |
458 |
$search = '#(?:' . $search . ')#i'; |
459 |
while (preg_match($search, $value)) { |
460 |
$value = preg_replace($search, '', $value); |
461 |
} |
462 |
return $value; |
463 |
} |
464 |
|
465 |
} |