0 laravel eloquent laravel-5 laravel-5.3 laravel-eloquent
我创建了一个通知,我正在将模型传递给:
class NewMessage extends Notification implements ShouldQueue
{
use Queueable;
protected $message;
public function __construct(Message $message)
{
$this->message = $message;
}
public function via()
{
return ['database'];
}
public function toArray()
{
Log::info($this->message);
return [
'message_id' => $this->message->id,
];
}
}
Run Code Online (Sandbox Code Playgroud)
这就是我调用通知的方式:
$message = Message::where('user_id', Auth::user()->id)
->where('message_id', $message_id)
->with('topic')
->get();
$user->notify(new NewMessage($message));
Run Code Online (Sandbox Code Playgroud)
问题是当通知打印日志 ( Log::info($this->message);) 时,topic关系没有显示出来。
但是,我发现如果我toArray()将 nofitication 类中的函数更改为这个,它打印出来的效果很好:
public function toArray()
{
$this->message->topic;
Log::info($this->message);
return [
'message_id' => $this->message->id,
];
}
Run Code Online (Sandbox Code Playgroud)
为什么?我该如何解决?
注意:此问题/答案仅与 Laravel < 5.6 相关。从 Laravel 5.6 开始,加载的关系也被序列化了,所以这个问题已经不是问题了。
您的通知设置为队列,并且Notification您正在扩展的类使用该SerializesModels特征。当具有SerializesModels特征的对象被序列化以放入队列时,该对象上包含的任何模型(例如您的消息)将仅替换为该模型的 id(消息 id)。当队列工作器反序列化您的通知以处理它时,它将使用该消息 ID 从数据库中重新检索消息。不幸的是,当发生这种情况时,不包括任何关系。
因此,即使您的消息在序列化时加载了主题关系,队列工作者处理通知时也不会加载主题关系。如果您需要通知中的主题,则需要重新加载它,如您所见。
您可以在此处的文档中阅读有关此内容的更多信息。相关部分引述如下:
在这个例子中,请注意我们能够将 Eloquent 模型直接传递到排队作业的构造函数中。由于
SerializesModels作业使用的特性,Eloquent 模型将在作业处理时优雅地序列化和反序列化。如果您的排队作业在其构造函数中接受 Eloquent 模型,则只有模型的标识符将被序列化到队列中。当作业真正被处理时,队列系统会自动从数据库中重新检索完整的模型实例。这对您的应用程序完全透明,并防止序列化完整的 Eloquent 模型实例可能出现的问题。
| 归档时间: |
|
| 查看次数: |
961 次 |
| 最近记录: |