Mail Templates July 1, 2006
Posted by rossoft in CakePHP.trackback
New template view for sending mail through SMTP
Example:
- file app/views/foo/mail_view.mail
<m:from name=”Miguel Ros” mail=”fake@teleline.es” />
<m:to>
fake1@gmail.com
</m:to>
<m:to>
fake2@teleline.es
</m:to>
<m:subject> Hi! That is the subject
</m:subject>
<m:body_text>
This is the plain body text
</m:body_text>
<m:body_html>
This is the HTML <b>Body</b>
</m:body_html>
<m:attach path=”/tmp/test1.txt” name=”test_file_1.txt” />
<m:attach path=”/tmp/test2.txt” />
- File views/foo/mail_view.thtml:
The mail has been sent
- Action in FooController:
function mail_view()
{
$this->view=’Mail’;
$this->render(); //render the mail_view.mail
$this->view=’View’;
$this->render(); //now the mail_view.thtml renders
}
Needs the WidgetHelper and PHPMailer class
Copy to app/views/mail.php
<?php
/**
* Mail Templates
* Sends email through a view
*
* The templates rendered must have extension .mail
*
* Uses:
* @link http://phpmailer.sourceforge.net/
* @see MailWidgetHelper
*
* @author RosSoft
* @version 0.1
* @license MIT
*
*
* Usage example:
* First, edit this file and change the define(’CONFIG_SMTP…
* with your ISP config.
*
* file views/foo/mail_view.mail
<m:from name=”Miguel Ros” mail=”rosmiguel@teleline.es” />
<m:to>
rossoft@gmail.com
</m:to>
<m:to>
rosmiguel@teleline.es
</m:to>
<m:subject> Hi! That is the subject
</m:subject>
<m:body_text>
This is the plain body text
</m:body_text>
<m:body_html>
This is the HTML <b>Body</b>
</m:body_html>
<m:attach path=”/tmp/test1.txt” name=”test_file_1.txt” />
<m:attach path=”/tmp/test2.txt” />
File views/foo/mail_view.thtml:
The mail has been set
Action in FooController:
function mail_view()
{
$this->view=’Mail’;
$this->render(); //render the mail_view.mail
$this->view=’View’;
$this->render(); //now the mail_view.thtml renders
}
*/
define(’CONFIG_SMTP_HOST’,'xxxx’);
define(’CONFIG_SMTP_USER’,'yyyy’);
define(’CONFIG_SMTP_PASS’,'zzzz’);
//Directory within VENDORS/
define(’PHPMAILER_SUBDIR’,'phpmailer’ . DS);
class MailView extends View
{
var $mail=null; //instance of MailAux
function render($action = null, $layout = null, $file = null)
{
$this->mail=& new MailAux;
$this->controller->mail=& $this->mail;
$file=null;
$this->load_helper(’MailWidget’);
if ($action==NULL)
{
$action=$this->action;
}
$file=$this->get_filename($action,’.mail’);
ob_start();
parent::render($action,$layout,$file);
ob_get_clean();
return $this->mail->send();
}
/**
* Adds a helper to the helpers array for loading it
* @param string $helper Name of the helper like ‘Javascript’
*/
function load_helper($helper)
{
if (!in_array($helper,$this->helpers))
{
$this->helpers[]=$helper;
}
}
/**
* Returns the filename associated with the action
* with the extension “.$ext”
*
* @param string $action If null, then current action
* @param string $ext Extension of the view template (with dot) Example: ‘.xml’
* @return string
*/
function get_filename($action,$ext)
{
$old_ext=$this->ext;
$this->ext=$ext;
$fn=$this->_getViewFileName($action);
$this->ext=$old_ext;
return $fn;
}
}
/**
* This object is the interface between MailView and MailWidgetHelper
*/
class MailAux extends Object
{
var $charset=’utf-8′;
var $from_mail=null;
var $from_name=”;
var $to=array();
var $subject=”;
var $body_text=null;
var $body_html=null;
var $attachments=array();
/**
* SMTP Configuration
*/
var $host=CONFIG_SMTP_HOST;
var $username=CONFIG_SMTP_USER;
var $password=CONFIG_SMTP_PASS;
/**
* It contains mailer error message or false if no
* error has occurred
*/
var $error=false;
function send()
{
vendor(PHPMAILER_SUBDIR. ‘class.phpmailer’);
$mail = new PHPMailer();
$mail->PluginDir = VENDORS .PHPMAILER_SUBDIR ;
$mail->SetLanguage(’en’,VENDORS .PHPMAILER_SUBDIR . ‘language’ . DS);
$mail->CharSet= $this->charset;
$mail->IsSMTP(); // send via SMTP
$mail->Host = $this->host; // SMTP servers
if ($this->username !==null)
{
$mail->SMTPAuth = true; // turn on SMTP authentication
$mail->Username = $this->username; // SMTP username
$mail->Password = $this->password; // SMTP password
}
$mail->From = $this->from_mail;
$mail->FromName = $this->from_name;
foreach ($this->to as $address)
{
$mail->AddAddress($address);
}
$mail->Subject = $this->subject;
if ($this->body_html)
{
$mail->IsHTML(true); // send as HTML
$mail->Body = $this->body_html;
$mail->AltBody = $this->body_text;
}
else
{
$mail->IsHtml(false);
$mail->Body = $this->body_text;
}
//$mail->WordWrap = 50; // set word wrap
foreach ($this->attachments as $attach)
{
$mail->AddAttachment($attach['path'],$attach['name'],’base64′,$attach['type']);
}
if (! $mail->Send())
{
$this->error=$mail->ErrorInfo;
$this->log(’Mail send:’ . $mail->ErrorInfo);
return false;
}
else
{
$this->error=false;
return true;
}
}
}
?>
Copy to app/views/helpers/mail_widget.php
<?php
/**
* MailWidgetHelper
*
* For usage with MailView
*
* @author RosSoft
* @version 0.1
* @license MIT
*/
class MailWidgetHelper extends WidgetHelper
{
var $tag=array( ‘m:from’,
‘m:to’,
‘m:subject’,
‘m:body_text’,
‘m:body_html’,
‘m:attach’);
/**
* m:from (Mail From)
* $attr['mail'] Mail
* $attr['name'] Name (optional)
*/
function tag_m_from($attr,$inner_html)
{
$this->view->mail->from_name=@$attr['name'];
$this->view->mail->from_mail=@$attr['mail'];
}
/**
* m:to (Mail To)
* $inner_html Destination address
*/
function tag_m_to($attr,$inner_html)
{
$this->view->mail->to[]=$this->_trim($inner_html);
}
/**
* m:subject (Mail Subject)
* $inner_html The subject
*/
function tag_m_subject($attr,$inner_html)
{
$this->view->mail->subject=$this->_trim($inner_html);
}
/**
* m:body_text Body in plain text
* $inner_html The body
*/
function tag_m_body_text($attr,$inner_html)
{
$this->view->mail->body_text=$inner_html;
}
/**
* m:body_html Body in html text
* $inner_html The body
*/
function tag_m_body_html($attr,$inner_html)
{
$this->view->mail->body_html=$inner_html;
}
/**
* m:attach Adds an attachment
* $attr['path'] The path of the file
* $attr['name'] Overrides the attachment name
* $attr['type'] MIME type
*/
function tag_m_attach($attr,$inner_html)
{
$path=$attr['path'];
$name=($attr['name'])? $attr['name'] : ”;
$type=($attr['type'])? $attr['type'] : ‘application/octet-stream’;
$this->view->mail->attachments[]=array( ‘path’=>$path,
‘name’=>$name,
‘type’=>$type);
}
/**
* Removes the spaces, tabs, newlines from
* the beginning and ending of the string
* @param string $string
* @return string
*/
function _trim($string)
{
preg_match(’/^[\n\t\s]*(.*)[\n\t\s]*$/’,$string,$matches);
return $matches[1];
}
}
?>
I used PHPMailer for a long time, but found it too buggy, but fixes are hard (weird code inside). Community support is almost non-existing (no traffic at mailing list). Last release one year old. API is ugly, since there are many instance variables you have to set directly (instead of using Setters()). Documentation is bad (rudimentary phpDoc API Documentation with not too much comments)
Then i found Swift:
http://www.swiftmailer.org/
[...] RosSoft » Mail Templates CakePHP Email templates. Looks a bit involved just to get a new rendering option (tags: cakephp email templates) [...]
Nice article.
Sebastian, thanks for the tip on Swift Mailer, i’ll be definitely checking it out.
I will check out too.. very nice.