This is an emailing extension that wraps SwiftMailer. This extension also allows you to create emails from view files. For more information about SwiftMailer can do, see http://swiftmailer.org
Resources ¶
Requirements ¶
- Yii 1.1.x
Documentation ¶
Please see the phpdocs (it is in fact well-documented). First read through the main phpdoc on the Mail.php file and then the Message.php file (both in the root directory).
Quick example to catch your interest ¶
This is an advanced example. It is not required that you use view files to generate the emails.
$message = new YiiMailMessage;
$message->view = 'registrationFollowup';
//userModel is passed to the view
$message->setBody(array('userModel'=>$userModel), 'text/html');
$message->addTo($userModel->email);
$message->from = Yii::app()->params['adminEmail'];
Yii::app()->mail->send($message);
Change Log ¶
See Google Code hosting page
Matt Kantor has been so gracious as to provide an update, including:
- Removed the "debug" option and associated behavior. In its place are the "logging" and "dryRun" options. Logging uses Yii::log() (you can set up a LogRoute to show flashes for the old behavior).
- Changed class names to be less likely to cause conflicts (requested in several bug reports).
- Made the extension usable from CConsoleApplication.
- Plenty of formatting and documentation fixes.
This is great
I was using PHPMailer and making a transition to this one now.
However, Getting Failures By-reference did not work for me. (http://swiftmailer.org/docs/failures-byreference)
thx thx thx + addImage()
Great, you save me !
to embedd image :
/** * Embedd an image in the message (must be in html) * @see http://swiftmailer.org/docs/embedding-files * @param string $image relative path * @return string the cid of the image to use in the src of <img> */ public function addImage( $image ) { if( Yii::app()->mail->viewPath !== null ) $basePath = Yii::getPathOfAlias( Yii::app()->mail->viewPath ); $fullPath = $basePath.$image; return $this->message->embed( Swift_Image::fromPath( $fullPath ) ); }
usefull links for newsletter design
http://www.campaignmonitor.com/blog/post/2533/a-guide-to-css-support-in-emai-2/
http://www.reachcustomersonline.com/2010/01/23/09.27.00/
Use it all the time
But really need to rename the Message class as I have to avoid database and models called Message.
Really nice, works like a charm
Love being able to use views for email templates!
thx
Only Message could be refactored to a little more descrptive MailMessage for example ;)
Great work
The only feature I wish it had is an email layout view. So I added that functionality from your other mail extension.
@jonah
Swif_SendmailTransport would be great indeed ! Tks for your help.
@soso
Right now both Swift_SmtpTransport and Swift_MailTransport are supported (see Mail::transportType). Guess I forgot about Swift_SendmailTransport. I will implant it if anyone needs it
Awesome
Great job jonah!
Two things I noticed:
The latest swift lib version is 4.0.6 while your extension comes with 4.0.5. There's no issue upgrading, I simply overwrote the 4.0.5 files and it works allright.
Do you think you can include support for other transports?
Cheers,
-soso
thanks Jonah
Good job!
Dowloadable now without subversion
Ok, I uploaded a file so you can just download it if you desire. Check the links again in the "Overview" tab
use svn checkout
No, there is not. You must get it from google code. See the links in the "Overview" tab
good, but
there is no file in google code...
addPart
Thank you for this extension.
But perhaps a little addon. If someone wants to send a multipart message, the addPart of SwiftMailer should be implemented, I did that the same way you do for rendering the body.
how do you install?
How do you install this module? Please help!
Nice, but..
I just had to downvote this because it's based on SwiftMailer 4.x which is under the horrible GPL license.
Will it work with SwiftMailer 3 ?
I don't want to use GPL code, but it works wonderfully - so nice job. :)
Using aliases
Use aliases instead of dirname(FILE)
file: YiiMail.php
public function registerScripts() { if (self::$registeredScripts) return; self::$registeredScripts = true; require Yii::getPathOfAlias('application.vendors').'/swiftMailer/classes/Swift.php'; Yii::registerAutoloader(array('Swift','autoload')); require Yii::getPathOfAlias('application.vendors').'/swiftMailer/swift_init.php'; }
Using Gmail
Anynone can post an exemple on how to use this extension with Gmail as SMTP server?
Thanks
How do I capture possible errors from the swift mailer?
If Yii::app()->mail->send($message) returns "0", in which case the mailing process failed at some point, how do I know what went wrong exactly?
simple change - great benefits :)
Now you have to provide search path for YiiMailMessage class. It is also hard to provide mock component for testing...
would be nice if you provide function that returns new empty Message object from Yii::app()->mail component. Then you could send messages like this:
$message = Yii::app()->mail->createNewMessage();
$message->subject = 'XXX';
...
Yii::app()->mail->send( $message );
Question
Is there any way to differ the mail sending to the background, so that you can continue working while the mail is being sent?
@luisloboborobia
@luisloboborobia
I recommend logging the email to the database (instead of sending it right away), and then have a (say hourly) cron job come by and send it later.
Mail server configuration
Hi I have been having trouble figuirng out how to chage the settings for which mail server will be connected to. Can somone please help me out? :)
insert extra headers???
Hi!
How Can I (or where) insert extra headers to the message?? cuz when I send a mail to xxx@hotmail.com the mail appears into the junk box
Regards
Themeable?
Does this extension support themes?
Selecting a mail server
I have ended up making a class the extends YiiMail that overwrites getTransport so that it uses system parameters in the main config to determine which SMTP mail server to connect to. It works well, but I'm just wondering why this isn't in the extension or have I missed something?
about SMTP
I want to know hot to config a SMTP server(Support servers that require username & password and/or encryption). Who can do me a favor, THX?
Bug with Bcc
If you are using setBcc() only without addTo(), then line YiiMail.php(189) fails:
$msg = 'Sending email to '.implode(', ', array_keys($message->to))."\n".
it should at least be:
$msg = 'Sending email to '.implode(', ', array_keys((array)$message->to))."\n".
How to set SMTP for this extension.
To set STMP, put this code under the 'components' part in your main.php in config folder.
Assume you put this extension under /protects/extensions/mail/.
'mail' => array( 'class' => 'application.extensions.mail.YiiMail', 'transportType' => 'smtp', 'transportOptions' => array( 'host' => 'xxx.xxx.xxx.xxx', 'username' => 'username', 'password' => 'password', ), 'viewPath' => 'application.views.mail', 'logging' => true, 'dryRun' => false ),
Very well... you should have idea how to set it, hope it helps. For transport options, you should look in the document for more.
Razzle fracking
Great component :) Although it took a little razzle fracking to realise the transportType must be lower case - d'oh!
Here's a sample set up for using gmail or google apps:
Download mail to protected/extensions/yii-mail in your application. (some of the examples use /mail instead of /yii-mail - just ensure they are consistent)
In protected/main/config.php
'import'=>array( ... 'application.extensions.yii-mail.*', ... ), ... 'components'=>array( ... 'mail' => array( 'class' => 'application.extensions.yii-mail.YiiMail', 'transportType'=>'smtp', /// case sensitive! 'transportOptions'=>array( 'host'=>'smtp.gmail.com', 'username'=>'yourgoogleemail@gmail.com', // or email@googleappsdomain.com 'password'=>'yourgooglemailpassword', 'port'=>'465', 'encryption'=>'ssl', ), 'viewPath' => 'application.views.mail', 'logging' => true, 'dryRun' => false ), ... ),
Then to test its all working, I amended the Contact action in /protected/controllers/siteController.php
public function actionContact() { $model=new ContactForm; if(isset($_POST['ContactForm'])) { $model->attributes=$_POST['ContactForm']; if($model->validate()) { $message = new YiiMailMessage(); $message->setTo( array('myemail@mydomain.com'=>'myname')); $message->setFrom(array($model->email=>$model->name)); $message->setSubject($model->subject); $message->setBody($model->body); $numsent = Yii::app()->mail->send($message); Yii::app()->user->setFlash('contact', 'Emails sent:'.$numsent.'\n'. 'Thank you for contacting us. We will respond to you as soon as possible.'); $this->refresh(); } } $this->render('contact',array('model'=>$model)); }
If you want to use a different transport service within the app then use:
// Create an email transport $mailer = new YiiMail(); $mailer->transportType='smtp'; $mailer->transportOptions=array( 'host'=>'smtp.gmail.com', 'username'=>'yourgmail@gmail.com', 'password'=>'yourgmailpassword', 'port'=>'465', 'encryption'=>'ssl', ); $message = new YiiMailMessage(); //, $contentType, $charset) ... // Use the email transport $numsent = $mailer->send($message);
How to use views?
Gentlemen, how can I use views and view variable?
I need to develop couple of email templates and use this extension any ideas?
Thanks in advance
Simply Beautiful
especially for a localhost setup. Thanks!
Problem with setFrom
Great extension and somehow easy to implement. Unfortunately I have a problem with 'setFrom' properly. Well, I can set an email and name but on the other side (gmail) the email won't appear... e.g.
$message->setFrom(email_from, name_from); $message->setTo(array( email_to => name_to));
then, in gmail
Why does 'email_to' appear as from email? Does that make any sense? Am I overseeing something obvious?
Thanks for help and advice! DF
view paths not localized
I also like this extension very much! Thanks @jonah.
But one very big improvement would be for YiiMailMessage.setBody() to use the normal view-search algorithm, including looking for localized versions of the view. I am emailing to people in various languages. I know the language of my recipient and want to send them an email in their own language.
localization of view paths
this solves the issue I reported in my previous comment. Sorry I should have made this one comment.
in YiiMailMessage.setBody():
//JJD $viewPath = Yii::getPathOfAlias(Yii::app()->mail->viewPath.'.'.$this->view).'.php'; $viewPath = $controller->getViewFile(Yii::app()->mail->viewPath.'.'.$this->view);
Perfect
I installed this extension for on project I am working on, and it works like champ. The best thing is that it supports views, so, you just simply create email folder, and place all email views/templates there. Thanks!
Gridview in template
Has anyone tried using a grid view in the email template ?
addPart method
Great extension! I've been using a old version of this one with some modifications so I can use it in Console Apps and use the addPart method of Swiftmailer.
One of the things I think is still missing in this extension is the possibility of adding alternative body using a view. So I added a method to your extension in YiiMailMessage:
public function addPart($body='', $contentType=null, $charset = null){ if ($this->view !== null) { if (!is_array($body)) $body = array('body'=>$body); if(isset(Yii::app()->controller)) $controller = Yii::app()->controller; else $controller = new CController('YiiMail'); // renderPartial won't work with CConsoleApplication, so use // renderInternal - this requires that we use an actual path to the // view rather than the usual alias $viewPath = Yii::getPathOfAlias(Yii::app()->mail->viewPath.'.'.$this->view).'.php'; $body = $controller->renderInternal($viewPath, array_merge($body, array('mail'=>$this)), true); } return $this->message->addPart($body, $contentType, $charset); }
So in my controller I do:
$msg = new YiiMailMessage(); ... $msg->view = 'path.to.html.view'; $msg->setBody(array('model' => $model), 'text/html'); $msg->view = 'path.to.plain.view'; $msg->addPart(array('model' => $model), 'text/plain'); Yii::app()->mail->send($msg);
Sorry if I'm wrong somewhere but I'm no expert.
.php extension and subject
Two things that were nice to have:
public static function sendMailTemplate($template,$to,$subst=array(),$type='text/plain') { $message = new YiiMailMessage; $message->view = $template; $message->setBody($subst, 'text/plain','utf-8'); # get subject $body = $message->message->getBody(); $lines = explode("\n",$body); $subject = array_shift($lines); $message->message->setBody(implode("\n",$lines), $message->message->getContentType() ); # set, send $message->setSubject($subject); $message->addTo($to); $message->from = Yii::app()->params['adminEmail']; Yii::app()->mail->send($message); }
transportType: php and Yii::app()->mail->send($message) always returns false
When transportType is set to smtp, this function works fine. But when transportType is set to php, it always returns false - even if the email is sent. Any ideas?
/** * Sends an email to the user. * This methods expects a complete message that includes to, from, subject, and body * * @param YiiMailMessage $message the message to be sent to the user * @return boolean returns true if the message was sent successfully or false if unsuccessful */ private function sendEmail(YiiMailMessage $message) { $sendStatus = false; if (Yii::app()->mail->send($message) > 0) $sendStatus = true; return $sendStatus; }
open_basedir restriction
I have a trouble with open_basedir restriction, so how can I use setCacheType() and setTempDir() methods through Yii::app()->mail ?
no layout
It looks like it's not possible to use a layout for outgoing mails. Is this something that will be implemented in the future?
@wisp
check this topic
PEAR
Thanks for extension.
Just as a suggestion - make option "usePear" true/false.
Some of web-servers have installed SwiftMailer as PEAR package, so why not to use them instead of "vendors" package
save send() to dbase? [solved]
I'm looking for a way to save information created on send() to a database (e.g. uid, message id, reply-to, date sent, etc. Anybody know a way of doing that with yii-mail?
I belief flourish femail returns the uid on send(). Is there a way of getting some kind of return from yii-mail? I'm looking for this information so that I can ultimately add a capability for fetching associated replies from an smtp server. For that being able to save the uid and/or message id with the subject, body, and to/from/cc/bcc would be excellent.
The answer is quite easy: swiftmailer has a set of methods for each part of the message that outputs to string. for example $message->toString() returns all the parts in string format. You can also isolate different parts of the message. Search the Swiftmailer documentation for discussion.
+1 on the documentation
I have only lightly tested this extension. It works :-)
What I want to comment about is the documentation - great documentation - as every extension should have!
Is it possible to create an email with html and plain text parts?
I would like to send a message with multiple parts, text/html and text/plain.
Is it possible already or would I need to follow the idea of this comment: http://www.yiiframework.com/extension/mail/#c4857 ?
localhost
This extension rocks!
I just want to know if somebody has an example of a configuration for a localhost mail using PostFix.
TIA!
Multiple recipients?
How can I send this to multiple recipients?
Should I repeat
I need to find the users(contacts) from the database like this
$users=C::model()->findAllByAttributes(array('c_id'=>$this->_c->id));
Thanks!
to RussellEngland
thanks RussellEngland but to me return this error -> "require_once(C:\web-dev\xampp\htdocs\myApp\protected\components\yii-mail\vendors\swiftMailer/dependency_maps/cache_deps.php) [function.require-once]: failed to open stream: No such file or directory
C:\web-dev\xampp\htdocs\myApp\protected\components\yii-mail\vendors\swiftMailer\swift_init.php(16)
"
why ? tnx
Non ASCI characters in subject and Windows Live Mail
I have a problem with russian characters in email subject. It makes email look incorrect in Windows Live Mail Client, so it looks like:
> =?utf-8?Q?=D1=86=D0=B8=D1=8F_=D0=B2?= .... etc.
In other mail clients it's all ok.
I found the temporary solution, it solved my problem, but it is very ugly. I encoded subject manually by base64 in YiiMailMessage.php:
public function setSubject($subject) { $this->message->setSubject('=?utf-8?B?'.base64_encode($subject).'?='); }
Could anybody help me? Thanks!
CC and BCC?
I don't see any implementation for either CC or BCC? Did I miss something?
If not, I'd like to add to the suggestion box that you include a wrapper for the SwiftMail CC and BCC functions in your extension.
Thanks :)
about cc, bcc
@ploaiza
the YiiMailMessage wrapper the Swift_message instance . and you can pass any method to the underlying swift_message obj from yiimailmessage obj :
$msg = new YiiMailMessage(); .. $msg->addCc('xx@xx.com','jhon'); $msg->setBcc(array('xx@xx.com','jj@jj.com'=>'jjName')); .. Yii::app()->mail->send($msg);
the usage is same to Swift_message
Great extension
First of all, I would like to thank you for this extension.
I would like to know if there is a way to configure it so as to start my defaul mail application with the mail so that I may view it in my mail application and do any modification there before sending. This would be so nice.
Thanks for your reply beforehand
File Translation
In order to use file translation for views you should include this line at YiiMailMessage.php:
$viewPath = Yii::getPathOfAlias(Yii::app()->mail->viewPath . '.' . $this->view) . '.php'; $viewPath = Yii::app()->findLocalizedFile($viewPath); // New line $body = $controller->renderInternal($viewPath, array_merge($body, array('mail' => $this)), true);
About Subject character encoding
@jedi-m
'=?utf-8?B?'.base64_encode($subject).'?='
is not only an ugly solution, it is THE solution :) at least with mail() when you have to use it if you have accented / non-latin characters.
The explanation is here. Quote:
> subject
Subject of the email to be sent.
Caution
Subject must satisfy » RFC 2047.
Fix sendSimple() function
To be able to use the sendSimple() function replace line 181 in YiiMail.php:
else return $this->getMailer()->send($message);
with
else return $this->getMailer()->send($message->message);
About Subject character encoding
@jdm instead of modifying the setSubject($subject) function, simply add the following code at the end of registerScripts() function in YiiMail.php
// set default preferrences Swift::init(function () { Swift_DependencyContainer::getInstance() ->register('mime.qpheaderencoder') ->asAliasOf('mime.base64headerencoder'); Swift_Preferences::getInstance()->setCharset(Yii::app()->charset); });
What this does is set correct encoding (i assume you have charset defined in main config) and encodes the subject automatically (the same way you did).
Gmail SMTP error
Hi!
How to configure this ext with Gmail?
I tried :
'mail' => array( 'class' => 'YiiMail', 'transportType' => 'smtp', 'transportOptions' => array( 'host'=>'smtp.gmail.com', 'username'=>'********', 'password'=>'********', 'port'=>'587', 'encryption'=>'tls' ), 'viewPath' => 'application.views.mail', 'logging' => true, 'dryRun' => false ),
I get :
fsockopen() [<a href='function.fsockopen'>function.fsockopen</a>]: SSL operation failed with code 1. OpenSSL Error messages: error:1408F10B:SSL routines:SSL3_GET_RECORD:wrong version number
I also tried :
'mail' => array( 'class' => 'YiiMail', 'transportType' => 'smtp', 'transportOptions' => array( 'host'=>'smtp.gmail.com', 'username'=>'********', 'password'=>'********', 'port'=>'465', 'encryption'=>'ssl' ), 'viewPath' => 'application.views.mail', 'logging' => true, 'dryRun' => false ),
wich gives this :
fsockopen() [<a href='function.fsockopen'>function.fsockopen</a>]: unable to connect to ssl://smtp.gmail.com:465 (Connection timed out)
Help, please?
Cheers!
From field cannot be set
$message->setFrom("admin@example.com");
has no effect for me. All the other options are fine (subject, body...) but the "from" is always the email address used in the username of main.php.
Any idea why ?
@Renaud
Try:
$message->from = "admin@example.com";
using setFrom
If you want to use $message->setFrom($email) you need to remove username (password) from the main.php and instead set it manually in your code:
Yii::app()->mail->getTransport()->setUsername('admin@example.com'); Yii::app()->mail->getTransport()->setPassword('adminpassword...'); .... $message->setFrom('admin@example.com');
I believe this is because you cannot have sender from one email address while you are actually sending the email from a different email account.
If your sender is always 'admin' then just set it in the main.php file. Otherwise use the method above.
@zdenekca
Thanks zdenekca for your answer
But actually what I want to do is set the sender as an email address that does not exist (like noreply@example.com)
From what you're telling me it seems not possible, is it ?
@Renaud
I believe that you can't set 'from' to be anything you like otherwise you could impersonate organizations (and people)?
Why don't you setup noreply@ account and send emails from this account. I see this being done by everyone else.
cheers
use setFrom / setSender
how to use setFrom / setSender??
because no effect for me.
found how to setFrom
just set like this
$message = new YiiMailMessage; $message->getHeaders()->addMailboxHeader('From');
and then you can set from like this
$message->setFrom('xxx@gmail.com');
you can read this
Gmail smtp config
'mail' => array( 'class' => 'ext.yii-mail.YiiMail', 'transportType' => 'smtp', 'transportOptions' => array( 'host' => 'smtp.gmail.com', 'username' => 'XXXX@gmail.com', 'password' => 'XXXX', 'port' => '465', 'encryption'=>'tls', ), 'viewPath' => 'application.views.mail', 'logging' => true, 'dryRun' => false ),
works
Setting up a connector to Mircosoft Exchange
This post helped me set up a trusted mail connector to MS Exchange:
http://blogs.technet.com/b/sbs/archive/2008/09/18/how-to-configure-trusted-smtp-relay-in-exchange-on-sbs-2008.aspx
How can I send an attachment?
I've trying this:
$uploadedFile = CUploadedFile::getInstance($model,'anexo');
$msg->attach($uploadedFile);
But doesn't work and give no errors... Just a blank page...
Adding attachments, embedding images
How do you:
a) Add an attachment (or multiple attachments).
b) Embed an image within the email.
Thanks for the extension !
Thanks for the extension !
I too, would like to know how to embed images in the e-mail. Right now, when using a view, the images used in the view are not displayed in the e-mail. Do you have a guide on how to do this ?
Thanks,
Jonathan
Embed image
Using the view you can easily show images. THe only thing that comes to my mind is that probably you have a problem with the src of the image, which has to be an absolute url.
Just guessing.
hi friends
Property "CWebApplication.mail" is not defined.
got always .
@rajesh chaurasia
Add line:
'application.extensions.yii-mail.*',
to config in import section
Track Bounce Email
How can i Track Bounce Emails
When SMTP host is not accessible, Swift_TransportException
Hi
Everything works fine! Thanks for the nice extension.
But if the mail server is not accessible, an exemption is thrown. Swift_TransportException
Connection could not be established with host smtp.mysite.com [php_network_getaddresses: getaddrinfo failed: No such host is known. #0]
It may not be a problem if the mail server is extremely reliable and offer maximum connectivity. But how to avoid this? Can we provide a try-catch loop for send function so that if the mail is not send we can take further actions for deferred sending and informing the user appropriately.
Tried providing try-catch and problem solved.
$result;
try {
} catch (Exception $e) {
$result=0;
}
Here we will get a $result which is more than 0 if there is no exception and the mail is sent.
Thanks
Nair
ContentType
When I use that extension (which is used Swift) to send email with attached file, I figured out that Swift trying to determine content type based on attached file extension, I'm thinking it's not safe decision. Just for a note ;)
code snippet for attaching a file.
for those of you interesting in attaching pdfs/jpegs or whatever you please, use this -
Enjoy!
Amazon SES issues
if you got this error:
This is because Yii-mail use a prehistoric version of swiftMailer.
Update SwiftMailer (located in the "vendor" directory) and it will works.
From email id not set . IT takes SMTP username.
From email id not set . IT takes SMTP username.
I have tried above solution but not working for me.
@TomaszKane
Hello
Regarding the config
This should be placed in under COMPONENTS. :)
'mail' => array( 'class' => 'ext.yii-mail.YiiMail', 'transportType' => 'smtp', 'transportOptions' => array( 'host' => 'smtp.gmail.com', 'username' => 'XXXX@gmail.com', 'password' => 'XXXX', 'port' => '465', 'encryption'=>'tls', ), 'viewPath' => 'application.views.mail', 'logging' => true, 'dryRun' => false ),
Thanks for the assist everyone
@bandpay
This should be in
components
config section.smtp
Hello bandpay,
if you don't find soluton then check the
Link
Error in Swift_TransportStreamBuffer::$sequence
If you get this error:
then change visibility of variable $_sequence from 'private' to 'protected' in 'yii-mail/vendors/swiftMailer/classes/Swift/ByteStream/AbstractFilterableInputStream.php'
possible problem with sendSimple() function
instead of
else return $this->getMailer()->send($message);
should be
else return $this->getMailer()->send($message->message);
If you have any questions, please ask in the forum instead.
Signup or Login in order to comment.