2015-10-07 135 views
3

我想从它的官方文档中学习laravel数据库队列。我已经完成了文档中给出的配置。Laravel 5.1没有关于排队模型的查询结果

这里我的工作:

<?php 

namespace App\Jobs; 

use App\SearchLog; 
use App\Jobs\Job; 
use Illuminate\Queue\SerializesModels; 
use Illuminate\Queue\InteractsWithQueue; 
use Illuminate\Contracts\Bus\SelfHandling; 
use Illuminate\Contracts\Queue\ShouldQueue; 

class SendTicket extends Job implements SelfHandling, ShouldQueue 
{ 
    use InteractsWithQueue, SerializesModels; 

    protected $log; 

    protected $searchLog = array(); 



    public function __construct(SearchLog $log , $data = array()) 
    { 
     $this->log = $log; 
     $this->searchLog = $data; 
    } 

    /** 
    * Execute the job. 
    * 
    * @return void 
    */ 
    public function handle() 
    { 

     $this->log->create($this->searchLog);  
    } 

在我的控制器我这样调用

public function store(Request $request) 
{ 
$searchLog = array(); 
// searchLog contains the data to be inserted into database 
$log = new SearchLog(); 
$this->dispatch(new SendTicket($log , $searchLog)); 
} 

当我运行php artisan queue:listen我得到这样

错误

[照亮\数据库\ Eloquent \ ModelNotFoundException]没有查询 模型[App \ SearchLog]的结果。

但是,当我编辑的职位像这样

//only edited code 
public function __construct($data = array()) 
{ 
    $this->searchLog = $data; 
} 

/** 
* Execute the job. 
* 
* @return void 
*/ 
public function handle() 
{ 
    SearchLog::create($this->searchLog); 
} 

当从这样的

public function store(Request $request) 
{ 
    $searchLog = array(); 
    // searchLog contains the data to be inserted into database 
    $this->dispatch(new SendTicket($searchLog)); 
} 

调用它工作正常,并插入数据。
在这里,我的问题是:

  1. 如何将对象发送到队列中?
  2. 将数据发送到队列以便我们可以处理的最佳方式是什么?
+0

这Laravel行为是意外这么多的人,所以我很高兴地看到,有是一个相关的错误报告在这里:https://github.com/laravel/framework/issues/14526 – Ryan

回答

0

我遇到了同样的问题。

看起来如果你想将模型推送到队列中,只有它的ID将被保存在有效载荷中。所以,如果你还没有保存模型,它不会在处理程序中可用。

毕竟我在documentation的章节Queues and Eloquent Models中找到它。

为了解决这个问题,我看到两个方案,第一就是要确保你有一个持久的型号:

public function store(Request $request) 
{ 
$searchLog = array(); 
// searchLog contains the data to be inserted into database 
$log = new SearchLog(); 
//Save the Searchlog beforehand if it doesn't have any data constraints 
$log->save(); 
//Dispatch the Job with the saved Model 
$this->dispatch(new SendTicket($log , $searchLog)); 
} 

把完整的模型保存过程中的处理程序而已,就像你在你的例子中做了。

//Full saving/initializing is happening here 
public function handle() 
{ 
    SearchLog::create($this->searchLog); 
} 

在我而言,我不得不模型保存到一个高性能的过程数据库,所以我把它完全在我的过程是不依赖于数据库保存速度的处理程序。所以我会把它放在handle()函数中。

2

问题出在use Illuminate\Queue\SerializesModels;,它试图序列化传递给构造函数的SearchLog $log参数。由于您的模型尚未保存,因此它没有标识符。

根据Laravel文档:

如果排队的作业接受其构造雄辩的模型中,只有 为模型标识将被序列化到队列中。当 实际处理作业时,队列系统将自动从数据库中重新检索完整模型实例 。

的解决方法是从作业类你愿意保存模型中删除SerializesModels特质。

+0

https://stackoverflow.com/a/42981667/470749是一个相关的问题,帮助我。 – Ryan