Queuing Mailables with Custom Headers in Laravel 5.4

The Problem

The Context

// Create a simple array for improved serialization!
$data = [
'email' => $recipient->email,
'name' => $recipient->name,
'source' => SocialGroup::class,
'id’ => 42,
];
$this->mailer->queue(
'announcement-posted', [
'announcement' => $announcement,
'recipient' => $recipient,
],
function ($m) use ($data) {
$m
->to($data[‘email’], $data[‘name’])
->subject(‘There’s a new announcement for you!’);
// Set some custom headers.
$m->getSwiftMessage()->getHeaders()->addTextHeader(‘X-Messagable-Source’, $data[‘source’]);
$m->getSwiftMessage()->getHeaders()->addTextHeader(‘X-Messagable-ID’, $data[‘id’]);
}
);

Knowing When To Do The Job

The Journey

namespace App\Mail;use Illuminate\Bus\Queueable;
use Illuminate\Mail\Mailable;
use Illuminate\Queue\SerializesModels;
use Illuminate\Contracts\Queue\ShouldQueue;
/**
* Overrides…
*/
use Illuminate\Container\Container;
use Illuminate\Contracts\Mail\Mailer as MailerContract;
abstract class AbstractMessage extends Mailable
{
use Queueable, SerializesModels;
/**
* Describes additional headers.
*
* @var array
*/
protected $headers = [];

public function __construct(array $headers = [])
{
$this->headers = $headers;
}
}
namespace App\Mail;class AnnouncementPosted extends AbstractMessage
{
/**
* Build the message.
*
* @return $this
*/
public function build()
{
return $this->subject('There’s a new announcement for you!')
->view(‘emails.announcement-posted’);
}
}
$headers = ['X-Special-Header' => 'The Cat Did It'];
Mail::to('bob@smith.com')->queue(new AnnouncementPosted($headers));
abstract class AbstractMessage extends Mailable
{
// ...
/**
* Send the message using the given mailer.
*
* @param \Illuminate\Contracts\Mail\Mailer $mailer
* @return void
*/
public function send(MailerContract $mailer)
{
Container::getInstance()->call([$this, 'build']);
$mailer->send($this->buildView(), $this->buildViewData(),
function ($message) {
$this->buildFrom($message)
->buildRecipients($message)
->buildSubject($message)
->buildAttachments($message)
->attachCustomHeaders($message) // This is new!
->runCallbacks($message);
});
}
// ...
}
abstract class AbstractMessage extends Mailable
{
// ...
/**
* Add custom headers to the message.
*
* @param \Illuminate\Mail\Message $message
* @return $this
*/
protected function attachCustomHeaders($message)
{
$swift = $message->getSwiftMessage();
$headers = $swift->getHeaders();
foreach ($this->headers as $header => $value) {
$headers->addTextHeader($header, $value);
}
return $this;
}
// ...
}

Why Does This Work Again?

Conclusion

--

--

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store