Laravel 5.7 包含的“电子邮件验证”功能运行良好,但异步电子邮件发送(在用户注册或重新发送链接页面期间)并不理想。
有没有办法通过队列发送电子邮件验证电子邮件而无需在 Laravel 5.7 中重写整个电子邮件验证?
Laravel 5.7 包含的“电子邮件验证”功能运行良好,但异步电子邮件发送(在用户注册或重新发送链接页面期间)并不理想。
有没有办法通过队列发送电子邮件验证电子邮件而无需在 Laravel 5.7 中重写整个电子邮件验证?
没有内置方式,但您可以通过扩展和覆盖轻松完成。
首先,创建一个扩展内置通知的新通知,并且还实现了 ShouldQueue 协定(以启用排队)。以下类假设您在以下位置创建通知app/Notifications/VerifyEmailQueued.php
:
namespace App\Notifications;
use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Auth\Notifications\VerifyEmail;
class VerifyEmailQueued extends VerifyEmail implements ShouldQueue
{
use Queueable;
// Nothing else needs to go here unless you want to customize
// the notification in any way.
}
现在您需要告诉框架使用您的自定义通知而不是默认通知。你可以通过覆盖sendEmailVerificationNotification()
你的User
模型来做到这一点。这只是改变了发送的通知。
public function sendEmailVerificationNotification()
{
$this->notify(new \App\Notifications\VerifyEmailQueued);
}
是的!这是可能的。要做到这一点,你将不得不重写sendEmailVerificationNotification
你的App\User
. 此方法由Illuminate\Auth\MustVerfiyEmail
trait 提供。该方法通过发送通知类中定义的电子邮件来sendEmailVerificationNotification
通知创建者。user
Illuminate\Auth\Notifications\VerifyEmail
// This is the code defined in the sendEmailVerificationNotification
public function sendEmailVerificationNotification()
{
$this->notify(new Notifications\VerifyEmail);
}
您可以将此方法更改为不直接通知用户。您将必须定义一个Job
您将在sendEmailVerificationNotification
方法中忽略的对象,而不是通知创建的用户。
在Job
课程中,您将创建一个handle
方法,您可以在其中将电子邮件发送到user
,但您必须将 提供$user
给 Job ,这可以通过将其作为参数传递给dispatch
方法来执行,如下所示:
public function sendEmailVerificationNotification()
{
VerifyEmail::dispatch($this);
}
$this
表示已创建user
,并且App\Jobs\VerififyEmail
作业(您将创建的)将接收传递给dispatch
其的所有参数__construct
的代码VerifyEmail
如下所示:
namespace App\Jobs;
use App\User;
use Illuminate\Bus\Queueable;
use Illuminate\Queue\SerializesModels;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
use Illuminate\Auth\Notifications\VerifyEmail;
class VerifyEmail implements ShouldQueue
{
use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
protected $user;
public function __construct(User $user)
{
$this->user = $user;
}
public function handle()
{
// Here the email verification will be sent to the user
$this->user->notify(new VerifyEmail);
}
}
我的解决方案是如果您要在控制器中手动注册用户。Laravel 已经创建了 Registered 事件和它的监听器 SendEmailVerificationNotification。
-首先在 .env 文件更新中配置应用程序中的队列QUEUE_CONNECTION=database
。有关更多队列文档,请阅读https://laravel.com/docs/6.x/queues
通过发布队列表php artisan queue:table
php artisan migrate
php artisan make:job EmailVerificationJob
在 EmailVerificationJob.php 添加公共变量
公共$用户;
在 EmailVerificationJob.php 构造函数中
公共函数 __construct(用户 $user) { $this->user = $user; }
在 EmailVerificationJob.php 处理函数中写入event(new Registered($this->user))
。
如果用户成功创建,则在您的控制器中添加此代码以使作业正常工作。
EmailVerificationJob::dispatch($user) ->delay(now()->addSeconds(5)); 这里作业延迟 5 秒。
最后,您必须启动 queue worker php artisan queue:work --tries=3
。这里的尝试意味着队列应该尝试多少次工作。
我在 Laravel 8 中使用的这个解决方案。
首先创建 SendEmailVerificationNotification 通知类
php artisan make:notification SendEmailVerificationNotification
app/Notifications/SendEmailVerificationNotification.php 文件内容将是这一项。这里我们将扩展 Laravel 默认的 SendEmailVerificationNotification 类并实现应该队列
<?php
namespace App\Notifications;
use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Notifications\Messages\MailMessage;
use Illuminate\Notifications\Notification;
class SendEmailVerificationNotification extends \Illuminate\Auth\Listeners\SendEmailVerificationNotification implements ShouldQueue
{
use Queueable;
}
最后一步是编辑 EventServiceProvider 类 $listen 数组。注释掉注册事件的默认通知并添加我们创建的自定义通知。
use App\Notifications\SendEmailVerificationNotification as QueuedSendEmailVerificationNotification;
use Illuminate\Auth\Events\Registered;
//use Illuminate\Auth\Listeners\SendEmailVerificationNotification;
protected $listen = [
Registered::class => [
// SendEmailVerificationNotification::class,
QueuedSendEmailVerificationNotification::class
],
];
解决方案非常简单:
Steps:
配置队列驱动程序
转到 --> Illuminate\Auth\Notifications\VerifyEmail
实现“ShouldQueue”接口并在上述类上添加一个特征“Queueable”,即“VerifyEmail”,如下所示:
类 VerifyEmail 扩展通知实现ShouldQueue { 使用Queueable;
.... .... ... }
3.就是这样
接口 & trait 的路径: 使用 Illuminate\Contracts\Queue\ShouldQueue;使用 Illuminate\Bus\Queueable;
请也检查文档: https ://laravel.com/docs/5.7/notifications#queueing-notifications