1: <?php
2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25:
26:
27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37: 38: 39: 40: 41: 42: 43: 44: 45: 46: 47: 48: 49: 50: 51: 52: 53: 54: 55: 56: 57: 58: 59: 60: 61: 62: 63: 64: 65: 66: 67: 68: 69:
70: class Mage_Core_Model_Email_Template extends Mage_Core_Model_Template
71: {
72: 73: 74:
75: const XML_PATH_TEMPLATE_EMAIL = 'global/template/email';
76: const XML_PATH_SENDING_SET_RETURN_PATH = 'system/smtp/set_return_path';
77: const XML_PATH_SENDING_RETURN_PATH_EMAIL = 'system/smtp/return_path_email';
78: const XML_PATH_DESIGN_EMAIL_LOGO = 'design/email/logo';
79: const XML_PATH_DESIGN_EMAIL_LOGO_ALT = 'design/email/logo_alt';
80:
81: protected $_templateFilter;
82: protected $_preprocessFlag = false;
83: protected $_mail;
84:
85: static protected $_defaultTemplates;
86:
87: 88: 89: 90:
91: protected function _construct()
92: {
93: $this->_init('core/email_template');
94: }
95:
96: 97: 98: 99: 100: 101: 102:
103: protected function _getLogoUrl($store)
104: {
105: $store = Mage::app()->getStore($store);
106: $fileName = $store->getConfig(self::XML_PATH_DESIGN_EMAIL_LOGO);
107: if ($fileName) {
108: $uploadDir = Mage_Adminhtml_Model_System_Config_Backend_Email_Logo::UPLOAD_DIR;
109: $fullFileName = Mage::getBaseDir('media') . DS . $uploadDir . DS . $fileName;
110: if (file_exists($fullFileName)) {
111: return Mage::getBaseUrl('media') . $uploadDir . '/' . $fileName;
112: }
113: }
114: return Mage::getDesign()->getSkinUrl('images/logo_email.gif');
115: }
116:
117: 118: 119: 120: 121: 122:
123: protected function _getLogoAlt($store)
124: {
125: $store = Mage::app()->getStore($store);
126: $alt = $store->getConfig(self::XML_PATH_DESIGN_EMAIL_LOGO_ALT);
127: if ($alt) {
128: return $alt;
129: }
130: return $store->getFrontendName();
131: }
132:
133: 134: 135: 136: 137:
138: public function getMail()
139: {
140: if (is_null($this->_mail)) {
141: $this->_mail = new Zend_Mail('utf-8');
142: }
143: return $this->_mail;
144: }
145:
146: 147: 148: 149: 150: 151:
152: public function setTemplateFilter(Varien_Filter_Template $filter)
153: {
154: $this->_templateFilter = $filter;
155: return $this;
156: }
157:
158: 159: 160: 161: 162:
163: public function getTemplateFilter()
164: {
165: if (empty($this->_templateFilter)) {
166: $this->_templateFilter = Mage::getModel('core/email_template_filter');
167: $this->_templateFilter->setUseAbsoluteLinks($this->getUseAbsoluteLinks())
168: ->setStoreId($this->getDesignConfig()->getStore());
169: }
170: return $this->_templateFilter;
171: }
172:
173: 174: 175: 176: 177: 178:
179: public function loadByCode($templateCode)
180: {
181: $this->addData($this->getResource()->loadByCode($templateCode));
182: return $this;
183: }
184:
185: 186: 187: 188: 189: 190:
191: public function loadDefault($templateId, $locale=null)
192: {
193: $defaultTemplates = self::getDefaultTemplates();
194: if (!isset($defaultTemplates[$templateId])) {
195: return $this;
196: }
197:
198: $data = &$defaultTemplates[$templateId];
199: $this->setTemplateType($data['type']=='html' ? self::TYPE_HTML : self::TYPE_TEXT);
200:
201: $templateText = Mage::app()->getTranslator()->getTemplateFile(
202: $data['file'], 'email', $locale
203: );
204:
205: if (preg_match('/<!--@subject\s*(.*?)\s*@-->/u', $templateText, $matches)) {
206: $this->setTemplateSubject($matches[1]);
207: $templateText = str_replace($matches[0], '', $templateText);
208: }
209:
210: if (preg_match('/<!--@vars\s*((?:.)*?)\s*@-->/us', $templateText, $matches)) {
211: $this->setData('orig_template_variables', str_replace("\n", '', $matches[1]));
212: $templateText = str_replace($matches[0], '', $templateText);
213: }
214:
215: if (preg_match('/<!--@styles\s*(.*?)\s*@-->/s', $templateText, $matches)) {
216: $this->setTemplateStyles($matches[1]);
217: $templateText = str_replace($matches[0], '', $templateText);
218: }
219:
220: 221: 222:
223: $templateText = preg_replace('#\{\*.*\*\}#suU', '', $templateText);
224:
225: $this->setTemplateText($templateText);
226: $this->setId($templateId);
227:
228: return $this;
229: }
230:
231: 232: 233: 234: 235:
236: static public function getDefaultTemplates()
237: {
238: if(is_null(self::$_defaultTemplates)) {
239: self::$_defaultTemplates = Mage::getConfig()->getNode(self::XML_PATH_TEMPLATE_EMAIL)->asArray();
240: }
241:
242: return self::$_defaultTemplates;
243: }
244:
245: 246: 247: 248: 249:
250: static public function getDefaultTemplatesAsOptionsArray()
251: {
252: $options = array(
253: array('value'=>'', 'label'=> '')
254: );
255:
256: $idLabel = array();
257: foreach (self::getDefaultTemplates() as $templateId => $row) {
258: if (isset($row['@']) && isset($row['@']['module'])) {
259: $module = $row['@']['module'];
260: } else {
261: $module = 'adminhtml';
262: }
263: $idLabel[$templateId] = Mage::helper($module)->__($row['label']);
264: }
265: asort($idLabel);
266: foreach ($idLabel as $templateId => $label) {
267: $options[] = array('value' => $templateId, 'label' => $label);
268: }
269:
270: return $options;
271: }
272:
273: 274: 275: 276:
277: public function getId()
278: {
279: return $this->getTemplateId();
280: }
281:
282: 283: 284: 285:
286: public function setId($value)
287: {
288: return $this->setTemplateId($value);
289: }
290:
291: 292: 293: 294: 295:
296: public function isValidForSend()
297: {
298: return !Mage::getStoreConfigFlag('system/smtp/disable')
299: && $this->getSenderName()
300: && $this->getSenderEmail()
301: && $this->getTemplateSubject();
302: }
303:
304: 305: 306: 307: 308:
309: public function getType(){
310: return $this->getTemplateType();
311: }
312:
313: 314: 315: 316: 317: 318:
319: public function getProcessedTemplate(array $variables = array())
320: {
321: $processor = $this->getTemplateFilter();
322: $processor->setUseSessionInUrl(false)
323: ->setPlainTemplateMode($this->isPlain());
324:
325: if (!$this->_preprocessFlag) {
326: $variables['this'] = $this;
327: }
328:
329: if (isset($variables['subscriber']) && ($variables['subscriber'] instanceof Mage_Newsletter_Model_Subscriber)) {
330: $processor->setStoreId($variables['subscriber']->getStoreId());
331: }
332:
333: if (!isset($variables['logo_url'])) {
334: $variables['logo_url'] = $this->_getLogoUrl($processor->getStoreId());
335: }
336: if (!isset($variables['logo_alt'])) {
337: $variables['logo_alt'] = $this->_getLogoAlt($processor->getStoreId());
338: }
339:
340: $processor->setIncludeProcessor(array($this, 'getInclude'))
341: ->setVariables($variables);
342:
343: $this->_applyDesignConfig();
344: try {
345: $processedResult = $processor->filter($this->getPreparedTemplateText());
346: }
347: catch (Exception $e) {
348: $this->_cancelDesignConfig();
349: throw $e;
350: }
351: $this->_cancelDesignConfig();
352: return $processedResult;
353: }
354:
355: 356: 357: 358: 359:
360: public function getPreparedTemplateText()
361: {
362: if ($this->isPlain() || !$this->getTemplateStyles()) {
363: return $this->getTemplateText();
364: }
365:
366: $html = "<style type=\"text/css\">\n%s\n</style>\n%s";
367: return sprintf($html, $this->getTemplateStyles(), $this->getTemplateText());
368: }
369:
370: 371: 372: 373: 374: 375: 376:
377: public function getInclude($template, array $variables)
378: {
379: $thisClass = __CLASS__;
380: $includeTemplate = new $thisClass();
381:
382: $includeTemplate->loadByCode($template);
383:
384: return $includeTemplate->getProcessedTemplate($variables);
385: }
386:
387: 388: 389: 390: 391: 392: 393: 394:
395: public function send($email, $name = null, array $variables = array())
396: {
397: if (!$this->isValidForSend()) {
398: Mage::logException(new Exception('This letter cannot be sent.'));
399: return false;
400: }
401:
402: $emails = array_values((array)$email);
403: $names = is_array($name) ? $name : (array)$name;
404: $names = array_values($names);
405: foreach ($emails as $key => $email) {
406: if (!isset($names[$key])) {
407: $names[$key] = substr($email, 0, strpos($email, '@'));
408: }
409: }
410:
411: $variables['email'] = reset($emails);
412: $variables['name'] = reset($names);
413:
414: ini_set('SMTP', Mage::getStoreConfig('system/smtp/host'));
415: ini_set('smtp_port', Mage::getStoreConfig('system/smtp/port'));
416:
417: $mail = $this->getMail();
418:
419: $setReturnPath = Mage::getStoreConfig(self::XML_PATH_SENDING_SET_RETURN_PATH);
420: switch ($setReturnPath) {
421: case 1:
422: $returnPathEmail = $this->getSenderEmail();
423: break;
424: case 2:
425: $returnPathEmail = Mage::getStoreConfig(self::XML_PATH_SENDING_RETURN_PATH_EMAIL);
426: break;
427: default:
428: $returnPathEmail = null;
429: break;
430: }
431:
432: if ($returnPathEmail !== null) {
433: $mailTransport = new Zend_Mail_Transport_Sendmail("-f".$returnPathEmail);
434: Zend_Mail::setDefaultTransport($mailTransport);
435: }
436:
437: foreach ($emails as $key => $email) {
438: $mail->addTo($email, '=?utf-8?B?' . base64_encode($names[$key]) . '?=');
439: }
440:
441: $this->setUseAbsoluteLinks(true);
442: $text = $this->getProcessedTemplate($variables, true);
443:
444: if($this->isPlain()) {
445: $mail->setBodyText($text);
446: } else {
447: $mail->setBodyHTML($text);
448: }
449:
450: $mail->setSubject('=?utf-8?B?' . base64_encode($this->getProcessedTemplateSubject($variables)) . '?=');
451: $mail->setFrom($this->getSenderEmail(), $this->getSenderName());
452:
453: try {
454: $mail->send();
455: $this->_mail = null;
456: }
457: catch (Exception $e) {
458: $this->_mail = null;
459: Mage::logException($e);
460: return false;
461: }
462:
463: return true;
464: }
465:
466: 467: 468: 469: 470: 471: 472: 473: 474: 475: 476:
477: public function sendTransactional($templateId, $sender, $email, $name, $vars=array(), $storeId=null)
478: {
479: $this->setSentSuccess(false);
480: if (($storeId === null) && $this->getDesignConfig()->getStore()) {
481: $storeId = $this->getDesignConfig()->getStore();
482: }
483:
484: if (is_numeric($templateId)) {
485: $this->load($templateId);
486: } else {
487: $localeCode = Mage::getStoreConfig('general/locale/code', $storeId);
488: $this->loadDefault($templateId, $localeCode);
489: }
490:
491: if (!$this->getId()) {
492: throw Mage::exception('Mage_Core', Mage::helper('core')->__('Invalid transactional email code: ' . $templateId));
493: }
494:
495: if (!is_array($sender)) {
496: $this->setSenderName(Mage::getStoreConfig('trans_email/ident_' . $sender . '/name', $storeId));
497: $this->setSenderEmail(Mage::getStoreConfig('trans_email/ident_' . $sender . '/email', $storeId));
498: } else {
499: $this->setSenderName($sender['name']);
500: $this->setSenderEmail($sender['email']);
501: }
502:
503: if (!isset($vars['store'])) {
504: $vars['store'] = Mage::app()->getStore($storeId);
505: }
506: $this->setSentSuccess($this->send($email, $name, $vars));
507: return $this;
508: }
509:
510: 511: 512: 513: 514: 515:
516: public function getProcessedTemplateSubject(array $variables)
517: {
518: $processor = $this->getTemplateFilter();
519:
520: if(!$this->_preprocessFlag) {
521: $variables['this'] = $this;
522: }
523:
524: $processor->setVariables($variables);
525:
526: $this->_applyDesignConfig();
527: try{
528: $processedResult = $processor->filter($this->getTemplateSubject());
529: }
530: catch (Exception $e) {
531: $this->_cancelDesignConfig();
532: throw $e;
533: }
534: $this->_cancelDesignConfig();
535: return $processedResult;
536: }
537:
538: public function addBcc($bcc)
539: {
540: if (is_array($bcc)) {
541: foreach ($bcc as $email) {
542: $this->getMail()->addBcc($email);
543: }
544: }
545: elseif ($bcc) {
546: $this->getMail()->addBcc($bcc);
547: }
548: return $this;
549: }
550:
551: 552: 553: 554: 555: 556:
557: public function setReturnPath($email)
558: {
559: $this->getMail()->setReturnPath($email);
560: return $this;
561: }
562:
563: 564: 565: 566: 567: 568:
569: public function setReplyTo($email)
570: {
571: $this->getMail()->setReplyTo($email);
572: return $this;
573: }
574:
575: 576: 577: 578: 579: 580:
581: protected function _parseVariablesString($variablesString)
582: {
583: $variables = array();
584: if ($variablesString && is_string($variablesString)) {
585: $variablesString = str_replace("\n", '', $variablesString);
586: $variables = Zend_Json::decode($variablesString);
587: }
588: return $variables;
589: }
590:
591: 592: 593: 594: 595: 596:
597: public function getVariablesOptionArray($withGroup = false)
598: {
599: $optionArray = array();
600: $variables = $this->_parseVariablesString($this->getData('orig_template_variables'));
601: if ($variables) {
602: foreach ($variables as $value => $label) {
603: $optionArray[] = array(
604: 'value' => '{{' . $value . '}}',
605: 'label' => Mage::helper('core')->__('%s', $label)
606: );
607: }
608: if ($withGroup) {
609: $optionArray = array(
610: 'label' => Mage::helper('core')->__('Template Variables'),
611: 'value' => $optionArray
612: );
613: }
614: }
615: return $optionArray;
616: }
617:
618: 619: 620: 621: 622:
623: protected function _beforeSave()
624: {
625: $code = $this->getTemplateCode();
626: if (empty($code)) {
627: Mage::throwException(Mage::helper('core')->__('The template Name must not be empty.'));
628: }
629: if($this->_getResource()->checkCodeUsage($this)) {
630: Mage::throwException(Mage::helper('core')->__('Duplicate Of Template Name'));
631: }
632: return parent::_beforeSave();
633: }
634: }
635: