Using Mailables in Laravel
Using Mailables in Laravel
Mailables in Laravel provide a convenient way to create and send email messages through a clean, fluent API. By using Mailables, you can encapsulate the logic for composing emails, making your code cleaner and more manageable. Here's how to effectively use Mailables in your Laravel application.
1. Creating a Mailable Class
To create a Mailable class, use the Artisan command:
php artisan make:mail OrderShipped
This command generates a new Mailable class in the app/Mail
directory.
Example: Mailable Class (app/Mail/OrderShipped.php
)
namespace App\Mail;
use Illuminate\Bus\Queueable;
use Illuminate\Mail\Mailable;
use Illuminate\Queue\SerializesModels;
class OrderShipped extends Mailable
{
use Queueable, SerializesModels;
public $order;
public function __construct($order)
{
$this->order = $order;
}
public function build()
{
return $this
->subject('Your Order Has Shipped')
->view('emails.orders.shipped');
}
}
Key Points:
- Constructor: The constructor can accept parameters to pass data to the email view. In this example, we pass an
$order
object. - Build Method: This method configures the email. You can set the subject, the view to be used, and attach files if needed.
2. Creating the Email View
You need to create a Blade view for the email. This view will contain the HTML or plain text content of the email.
Example: Email View (resources/views/emails/orders/shipped.blade.php
)
<!DOCTYPE html> <html> <head> <title>Order Shipped</title> </head> <body> <h1>Your Order has Shipped!</h1> <p>Order ID: {{ $order->id }}</p> <p>Thank you for your purchase!</p> </body> </html>
3. Sending Emails with Mailables
To send an email using your Mailable class, use the Mail
facade. You can specify the recipient's email address and the Mailable class.
Example: Sending an Email in a Controller
use App\Mail\OrderShipped;
use Illuminate\Support\Facades\Mail;
public function shipOrder($orderId)
{
$order = Order::findOrFail($orderId);
// Send the email
Mail::to($order->user->email)->send(new OrderShipped($order));
return response()->json(['message' => 'Order shipped email sent.']);
}
4. Queueing Emails
To improve performance, especially when sending bulk emails, you can queue your Mailable for later delivery.
Sending Queued Emails
Instead of using send()
, use the queue()
method:
Mail::to($order->user->email)->queue(new OrderShipped($order));
5. Customizing Mailable Content
You can customize the content of your Mailable based on dynamic data. For example, you could use different views or subjects based on the order status.
Example: Dynamic Subject and View
public function build()
{
if ($this->order->status === 'shipped') {
return $this
->subject('Your Order Has Shipped')
->view('emails.orders.shipped');
} else {
return $this
->subject('Your Order is Being Processed')
->view('emails.orders.processing');
}
}
6. Adding Attachments
You can attach files to your email using the attach()
method within the build()
method of your Mailable class.
Example: Attaching a File
public function build()
{
return $this
->subject('Your Order Has Shipped')
->view('emails.orders.shipped')
->attach('/path/to/file.pdf');
}
7. Using Markdown for Emails
Laravel allows you to create Markdown-based emails for better styling and structure. You can generate a Mailable with Markdown support.
Generating a Markdown Mailable
php artisan make:mail OrderShipped --markdown=emails.orders.shipped
Example Markdown Email View (resources/views/emails/orders/shipped.blade.php
)
@component('mail::message') # Your Order has Shipped! Order ID: {{ $order->id }} Thank you for your purchase! @component('mail::button', ['url' => '']) View Order @endcomponent Thanks,<br> {{ config('app.name') }} @endcomponent
8. Testing Mailables
You can test your Mailables locally by using a service like Mailtrap or MailHog. This allows you to view your emails without sending them to real users.
Configuring Mailtrap
Update your .env
file to use Mailtrap:
MAIL_MAILER=smtp MAIL_HOST=smtp.mailtrap.io MAIL_PORT=2525 MAIL_USERNAME=your_mailtrap_username MAIL_PASSWORD=your_mailtrap_password MAIL_ENCRYPTION=null MAIL_FROM_ADDRESS=noreply@example.com MAIL_FROM_NAME="${APP_NAME}"