A mailable is one email as a class. php artisan make:mail OrderShipped --markdown=mail.orders.shipped creates it and its template. Public constructor properties reach the template, envelope() holds the addressing and content() names the view:
public function __construct(public Order $order) {}
public function envelope(): Envelope
{
return new Envelope(
from: new Address('orders@example.com', 'Bookshop Orders'),
replyTo: [new Address('help@example.com', 'Bookshop Help')],
subject: "Order #{$this->order->id} has shipped",
tags: ['shipping'],
metadata: ['order_id' => $this->order->id],
);
}
public function content(): Content
{
return new Content(markdown: 'mail.orders.shipped');
}Mail::to($order->customer)->send(new OrderShipped($order)) sends it. to() takes an address or any model with email and name, and over SMTP the returned SentMessage carried 5lb1Rt6Zi5aqQW7AUNgFCk, the ID in Mailpit's reply. Without from, MAIL_FROM_ADDRESS applies. SerializesModels stores only the order's key when the mail is queued, and tags and metadata become X-Tag and X-Metadata-order_id headers, which API transports map to their own fields.