我正在处理一个队列作业,它从其他api导入一些数据并存储它们。
从我的控制器,当我说$this->dispatchNow(new ImportPatentsJob($numbers, $count, $invention_id, $redisId));
时,它工作得很好,过程没有失败。
但是,当我将其更改为dispatch
并对作业进行排队,然后通过队列工作器运行它时,它失败了。我的工作是这样的:
protected $numbers;
protected $count;
protected $invention_id;
protected $redisId;
/**
* Create a new job instance.
*
* @return void
*/
public function __construct($numbers, $count, $invention_id, $redisId)
{
$this->numbers = $numbers;
$this->count = $count;
$this->invention_id = $invention_id;
$this->redisId = $redisId;
$this->onQueue('import');
$this->setUpClients();
}
protected function setUpClients()
{
$this->imageClient = new Client([
'base_uri' => 'some-uri',
'headers' => ['API-TOKEN' => env('API_TOKEN')],
]);
$this->dataClient = new Client([
'base_uri' => 'some-uri',
'headers' => ['API-TOKEN' => env('API_TOKEN')],
]);
$this->familyClient = new Client([
'base_uri' => 'some-uri',
'headers' => ['API-TOKEN' => env('API_TOKEN')],
]);
}
/**
* Execute the job.
*
* @return void
*/
public function handle()
{
$folder_id = $this->createFolder();
$currentCount = 0;
foreach ($this->numbers as $number) {
$currentCount++;
Redis::executeRaw(['SET', 'importlog:' . $this->redisId, 'Import ' . $number['number']]);
try {
$response = $this->dataClient->get($number['number']); // this is line 85 where the exception occurs
} catch ('Exception $e) {
Redis::executeRaw(['SET', 'importlog:' . $this->redisId . ':fail:' . $number['number'], 'Could not import']);
Log::info($e);
continue;
}
$data = $this->decodeData($response);
$patent_id = $this->createPatentDocument($data, $folder_id);
$this->createPatentAddresses($data, $patent_id);
$this->createPatentApplications($data, $patent_id);
$this->createPatentPriorities($data, $patent_id);
$this->createPatentCitations($data, $patent_id);
$this->createPatentTaxonomies($data, $patent_id);
$this->createPatentTitles($data, $patent_id);
$this->createPatentAbstracts($data, $patent_id);
$this->createPatentClaims($data, $patent_id);
$this->createPatentDescriptions($data, $patent_id);
$this->createInventionResults($this->invention_id, $patent_id, $number['position']);
try {
$response = $this->imageClient->get($data['bibliographic']['root']['family']);
$blob = $this->fetchImageBlob($response, $number['number']);
if ($blob) {
$this->createFile($blob, $patent_id);
}
} catch ('Exception $e) {
Redis::executeRaw([
'SET',
'importlog:' . $this->redisId . ':fail:image:' . $number['number'],
'Patent number: ' . $number['number'] . '; Family number: ' . $data['bibliographic']['root']['family'],
]);
}
Redis::executeRaw([
'SET',
'importlog:' . $this->redisId . ':progress',
"Import progress: " . $currentCount . '/' . $this->count . '(' . ($currentCount / $this->count * 100) . '%)'
]);
}
}
它在我在try catch语句中说Log::info($e)
时失败。异常如下:
[2016-08-11 07:01:11] local.INFO: exception 'ErrorException' with message 'Undefined property: Uppdragshuset'AO'Tenant'Jobs'ImportPatentsJob::$dataClient' in /Users/rohan0793/Code/tenant-application/tenant-package/src/Jobs/ImportPatentsJob.php:85
Stack trace:
#0 /Users/rohan0793/Code/tenant-application/tenant-package/src/Jobs/ImportPatentsJob.php(85): Illuminate'Foundation'Bootstrap'HandleExceptions->handleError(8, 'Undefined prope...', '/Users/rohan079...', 85, Array)
#1 [internal function]: Uppdragshuset'AO'Tenant'Jobs'ImportPatentsJob->handle()
#2 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Container/Container.php(507): call_user_func_array(Array, Array)
#3 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Bus/Dispatcher.php(82): Illuminate'Container'Container->call(Array)
#4 [internal function]: Illuminate'Bus'Dispatcher->Illuminate'Bus'{closure}(Object(Uppdragshuset'AO'Tenant'Jobs'ImportPatentsJob))
#5 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(150): call_user_func(Object(Closure), Object(Uppdragshuset'AO'Tenant'Jobs'ImportPatentsJob))
#6 [internal function]: Illuminate'Pipeline'Pipeline->Illuminate'Pipeline'{closure}(Object(Uppdragshuset'AO'Tenant'Jobs'ImportPatentsJob))
#7 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(103): call_user_func(Object(Closure), Object(Uppdragshuset'AO'Tenant'Jobs'ImportPatentsJob))
#8 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Bus/Dispatcher.php(83): Illuminate'Pipeline'Pipeline->then(Object(Closure))
#9 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Queue/CallQueuedHandler.php(41): Illuminate'Bus'Dispatcher->dispatchNow(Object(Uppdragshuset'AO'Tenant'Jobs'ImportPatentsJob))
#10 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Queue/Jobs/Job.php(130): Illuminate'Queue'CallQueuedHandler->call(Object(Illuminate'Queue'Jobs'RedisJob), Array)
#11 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Queue/Jobs/RedisJob.php(50): Illuminate'Queue'Jobs'Job->resolveAndFire(Array)
#12 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Queue/Worker.php(213): Illuminate'Queue'Jobs'RedisJob->fire()
#13 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Queue/Worker.php(157): Illuminate'Queue'Worker->process('redis', Object(Illuminate'Queue'Jobs'RedisJob), 0, 0)
#14 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Queue/Console/WorkCommand.php(126): Illuminate'Queue'Worker->pop(NULL, 'import', 0, 3, 0)
#15 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Queue/Console/WorkCommand.php(79): Illuminate'Queue'Console'WorkCommand->runWorker(NULL, 'import', 0, 128, false)
#16 [internal function]: Illuminate'Queue'Console'WorkCommand->fire()
#17 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Container/Container.php(507): call_user_func_array(Array, Array)
#18 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Console/Command.php(169): Illuminate'Container'Container->call(Array)
#19 /Users/rohan0793/Code/tenant-application/vendor/symfony/console/Command/Command.php(256): Illuminate'Console'Command->execute(Object(Symfony'Component'Console'Input'ArgvInput), Object(Symfony'Component'Console'Output'ConsoleOutput))
#20 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Console/Command.php(155): Symfony'Component'Console'Command'Command->run(Object(Symfony'Component'Console'Input'ArgvInput), Object(Symfony'Component'Console'Output'ConsoleOutput))
#21 /Users/rohan0793/Code/tenant-application/vendor/symfony/console/Application.php(791): Illuminate'Console'Command->run(Object(Symfony'Component'Console'Input'ArgvInput), Object(Symfony'Component'Console'Output'ConsoleOutput))
#22 /Users/rohan0793/Code/tenant-application/vendor/symfony/console/Application.php(186): Symfony'Component'Console'Application->doRunCommand(Object(Illuminate'Queue'Console'WorkCommand), Object(Symfony'Component'Console'Input'ArgvInput), Object(Symfony'Component'Console'Output'ConsoleOutput))
#23 /Users/rohan0793/Code/tenant-application/vendor/symfony/console/Application.php(117): Symfony'Component'Console'Application->doRun(Object(Symfony'Component'Console'Input'ArgvInput), Object(Symfony'Component'Console'Output'ConsoleOutput))
#24 /Users/rohan0793/Code/tenant-application/vendor/laravel/framework/src/Illuminate/Foundation/Console/Kernel.php(107): Symfony'Component'Console'Application->run(Object(Symfony'Component'Console'Input'ArgvInput), Object(Symfony'Component'Console'Output'ConsoleOutput))
#25 /Users/rohan0793/Code/tenant-application/artisan(36): Illuminate'Foundation'Console'Kernel->handle(Object(Symfony'Component'Console'Input'ArgvInput), Object(Symfony'Component'Console'Output'ConsoleOutput))
#26 {main}
它说dataClient
属性是未定义的,但我不知道为什么。它的定义非常明确,当作业没有排队时,它可以很好地工作。我做错了什么?
所以我意识到我忘了为客户声明受保护的属性。但是当我这样做的时候,我遇到了这个错误。作业不再排队,但它异常显示:Serialization of 'Closure' is not allowed
我假设我无法序列化和存储Guzzle客户端
所以Guzzle闭包没有被序列化,因为它不能序列化闭包。这就是让我困惑的地方。
Exception: Serialization of 'Closure'
如果你有同样的问题,可以从这里开始。
我用一种更简单的方法解决了它。我只是在句柄方法中移动了客户端的声明,并使它们成为局部变量,在这种情况下,它们不必被序列化,只是坐在那里,直到某些作业使用它们。