Laravel8 Mailable 本文を動的にセット
Mailable使ったメール送信の場合、必ずbladeテンプレートを使う必要がある。
Mail::to(‘info@hoge.co.jp’)->send(Mailableクラスインスタンス);
別途Mailableを継承したクラスを作成し、
その中でメール本文に該当するbladeテンプレートを指定する。
Mailableを使ったメール送信のサンプルコードはGoogleで検索するとたくさん出てくるのでここでは割愛する。
今回やりたいことはこうだ。
とあるシステムでは、メール本文をデータベースで管理している。
更に本文は、Smartyテンプレート形式を採用しており、
送信前に、必要な変数には該当するテーブルの該当するカラムの値に置き換えて送信される。
こういう仕様のシステムの一部をLaravelに置き換える必要があり色々と試した。
- bladeじゃなくsmartyを使ってメール本文を構築できるか
- Mailableを使わないでメール送信してみるか
結果、うまくいかずbladeを使ってやってみるが、
データベース上に無数にあるメール本文データを全てbladeファイルに変換するのは効率が悪すぎるし
いつどこで誰が本文を変えるかわからない。
相当な時間を費やし、発想からものすごく簡単な方法で解決した。
email.blade.phpを作成する
resources/views/emails/email.blade.php
{{$context}}
内容はこれだけ。
で、context変数に、Smartyでビルドした本文をセットするだけ
app/Mail/HogeMail.php
namespace App\Mail;
use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Mail\Mailable;
use Illuminate\Queue\SerializesModels;
use SmartyBC;
class HogeMail extends Mailable
{
use Queueable, SerializesModels;
public $data;
/**
* Create a new message instance.
*
* @return void
*/
public function __construct($data)
{
$this->data = $data;
}
/**
* Build the message.
*
* @return $this
*/
public function build()
{
$smarty = new SmartyBC();
// Smartyテンプレート用の置き換え変数
$replacement = [
'hoge' => 'hogehoge'
];
$smarty->assign($replacement);
$template = $smarty->fetch('string:'.$source); // $sourceはデータベースに保存された本文
return $this->from($this->data['email'], $this->data['name'])
->subject('件名')
->text('emails.email')
->with(['context' => $template]);
}
}
bladeテンプレート側は、変数一個だけ用意して
ビジネスロジックからメール本文をゴッソリ変数で渡すだけ。
メール本文の数だけbladeテンプレートを作る必要が無い場合は
こんな方法もアリっちゃアリなのかな。