To send emails from Laravel, we are going to use the Swift Mailer library, which is already included by default in the Laravel package. Swift Mailer is a component-based library for sending e-mails from PHP applications.
In this article, you'll learn how to send emails using the Mail class of Laravel for the most known emails providers : Gmail, Outlook and Zoho. Besides, in case you don't want to do it in the laravel way, you'll learn how to send emails using plain Swift Mailer too.
Configuration
We need an account from where the Emails will be sent : an email account, the password , its SMTP server address and the type of encryption that it uses. Normally using SwiftMailer, you can provide these parameters while you send the email (see the Using plain SwiftMailer paragraph at the end of this article), however as a good practice in Laravel, we are going to provide these parameters in the .env
file in the root of your Laravel project.
The .env
file should contain as default the following values:
MAIL_DRIVER=null
MAIL_HOST=null
MAIL_PORT=null
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null
According to your email provider, the information is totally different, therefore we are going to provide you with the information of the most known email providers (do not forget to change the email and password):
Gmail
Note: is important to know that sometimes , the gmail accounts doesn't allow to send mails with swiftmailer and you need to uncheck the property "Allows the use on unsafe devices" in your gmail account.
MAIL_DRIVER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=465
MAIL_USERNAME=MyGoogleAccount
MAIL_PASSWORD=MyGooglePassword
MAIL_ENCRYPTION=ssl
Outlook
Outlook uses TLS encryption in the port 587 unlike Gmail or Zoho.
MAIL_DRIVER=smtp
MAIL_HOST=smtp-mail.outlook.com
MAIL_PORT=587
MAIL_USERNAME=MyOutlookAccount
MAIL_PASSWORD=MyOutlookPassword
MAIL_ENCRYPTION=tls
Zoho
MAIL_DRIVER=smtp
MAIL_HOST=smtp.zoho.com
MAIL_PORT=465
MAIL_USERNAME=MyZohoEmail
MAIL_PASSWORD=MyZohoPassword
MAIL_ENCRYPTION=ssl
Other providers
The following table provides a list of the most know email providers with it respective SMTP address.
PROVIDER | URL | SMTP SETTINGS |
---|---|---|
1&1 | 1and1.com | smtp.1and1.com |
Airmail | Airmail.net | mail.airmail.net |
AOL | Aol.com | Smtp.aol.com |
AT&T | Att.net | Outbound.att.net |
Bluewin | Bluewin.ch | smtpauths.bluewin.ch |
BT Connect | Btconnect.com | mail.btconnect.tom |
Comcast | Comcast.net | smtp.comcast.net |
Earthlink | Earthlink.net | smtpauth.earthlink.net |
Gmail | Gmail.com | smtp.gmail.com |
Gmx | Gmx.net | mail.gmx.net |
HotPop | Hotpop.com | mail.hotpop.com |
Libero | Libero.it | mail.libero.it |
Lycos | Lycos.com | smtp.lycos.com |
O2 | o2.com | smtp.o2.com |
Orange | Orange.net | smtp.orange.net |
Outlook.com (former Hotmail) | Outlook.com | smtp.live.com |
Tin | Tin.it | Mail.tin.it |
Tiscali | Tiscali.co.uk | smtp.tiscali.co.uk |
Verizon | Verizon.net | outgoing.verizon.net |
Virgin | Virgin.net | smtp.virgin.net |
Wanadoo | Wanadoo.fr | smtp.wanadoo.fr |
Yahoo | Yahoo.com | smtp.mail.yahoo.com |
Zoho | zoho.com/mail/ | smtp.zoho.com |
Note: you can use those values for send emails using plain SwiftMailer.
Sending email
After the modification of the .env file, do not forget to clear the cache using the following command in your Laravel project :
php artisan cache:clear
Now, we can start writing some code in the controllers to send emails. Laravel uses Swift Mailer to send emails, in this way we can easily send emails. The e-mail templates are loaded in the same way as views does, so you can use the Blade syntax and inject data into your templates.
In this case we are going to create an email template in the resources/views
folder with the name email_template.blade.php
. It will contain the basic email template that will be sent in the demo.
Plain text
The mail wrapper allow you to send plain text mails easily, just include use the Mail
namespace.
<?php
namespace App\Http\Controllers;
use App\Http\Controllers\Controller;
use Mail;
class DefaultController extends Controller
{
/**
* Send plain text email
*/
public function mail()
{
$data = array('name'=>"Our Code World");
// Path or name to the blade template to be rendered
$template_path = 'email_template';
Mail::send(['text'=> $template_path ], $data, function($message) {
// Set the receiver and subject of the mail.
$message->to('[email protected]', 'Receiver Name')->subject('Laravel First Mail');
// Set the sender
$message->from('[email protected]','Our Code World');
});
return "Basic email sent, check your inbox.";
}
}
And the blade template content :
<!--
/resources/views/email_template.blade.php
-->
Some plain text that my user will receive, 1 > 2 = false
HTML
Sending HTML multipart emails is easier than you thinks thanks to SwiftMailer, provide as first parameter the name of the template in the send method instead of an array and you're ready to go.
<?php
namespace App\Http\Controllers;
use App\Http\Controllers\Controller;
use Mail;
class DefaultController extends Controller
{
/**
* Send HTML email
*/
public function htmlmail()
{
$data = array('name'=>"Our Code World");
// Path or name to the blade template to be rendered
$template_path = 'email_template';
Mail::send($template_path, $data, function($message) {
// Set the receiver and subject of the mail.
$message->to('[email protected]', 'Receiver Name')->subject('Laravel HTML Mail');
// Set the sender
$message->from('[email protected]','Our Code World');
});
return "Basic email sent, check your inbox.";
}
}
And the blade template:
<!--
/resources/views/email_template.blade.php
-->
<h1>Hey, how you doing bro?</h1>
I have some info for you, please visit my blog <a href="http://ourcodeworld.com">here</a>.
Using plain SwiftMailer
If you don't want to modify the .env environment or you use more than 1 email account, then you need to write your email sender by yourself using the Swift Mailer class. But don't worry, it isn't so complicated as it sounds, working with SwiftMailer is easy and fun.
Note that
<?php
namespace App\Http\Controllers;
use App\Http\Controllers\Controller;
use Mail;
use View;
class DefaultController extends Controller
{
public function email(){
// Configuration
$smtpAddress = 'smtp.zoho.com';
$port = 465;
$encryption = 'ssl';
$yourEmail = '[email protected]';
$yourPassword = 'mypassword';
// Prepare transport
$transport = \Swift_SmtpTransport::newInstance($smtpAddress, $port, $encryption)
->setUsername($yourEmail)
->setPassword($yourPassword);
$mailer = \Swift_Mailer::newInstance($transport);
// Prepare content
$view = View::make('email_template', [
'message' => '<h1>Hello World !</h1>'
]);
$html = $view->render();
// Send email
$message = \Swift_Message::newInstance('Test')
->setFrom(['[email protected]' => 'Our Code World'])
->setTo(["[email protected]" => "[email protected]"])
// If you want plain text instead, remove the second paramter of setBody
->setBody($html, 'text/html');
if($mailer->send($message)){
return "Check your inbox";
}
return "Something went wrong :(";
}
}
And the content of the blade template :
<!--
/resources/views/email_template.blade.php
-->
This will be escaped
{{ $message }}
<br>
But this not {!! $message !!}
Recommendations
- You can wrap all the mail functions inside a command to keep your controllers thin as possible.
- You may wish to create a
resources/views/emails
directory to house all of your email templates; however, you are free to place them wherever you wish within yourresources/views
directory.
Have fun !