0

I have a batch that calculates a score for many models. There is a horizon worker that process the batch, and most of the times, it runs with success. However, sometimes, a job CalculateFieldScores fails with the message No query results for model [Mz\Models\Ipa\Category]. The Category table in the database haven't change for more than a year, so it should always exist. enter image description here enter image description here Here is the code.

CalculateCategoryScores

<?php

namespace Mz\Jobs\IPA;

use Illuminate\Bus\Queueable;
use Illuminate\Queue\SerializesModels;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
use Mz\Models\Ipa\Category;
use Illuminate\Support\Facades\Bus;
use Mz\Models\Ipa\Field;

class CalculateCategoryScores implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;

    private $categories;
    private $fields;

    public $timeout = 86400;

    public function __construct()
    {
        $this->categories = Category::actives()->with('conditions')->get();
        $this->fields = Field::actives()->with('conditions')->get();
    }

    public function handle()
    {
        foreach($this->categories as $category) {
            $fields = $this->getFieldsByCategoryAssignation($category);
            foreach($fields as $field) {
                $batchable[] = new CalculateFieldScore($category, $field);
            }
        }
        Bus::batch($batchable)
        ->then(function($batch) {
            (new BuildTemporaryTables)->handle();
        })
        ->dispatch();
    }

    private function getFieldsByCategoryAssignation($category)
    {
        return $this->fields->filter(function($field) use ($category) {
            return $field->Assignation === 0 || $field->Assignation === $category->Assignation;
        });
    }
}

And this is the job thats sometimes fails:

<?php

namespace Mz\Jobs\IPA;

use Illuminate\Bus\Queueable;
use Illuminate\Queue\SerializesModels;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
use Mz\Models\Ipa\Category;
use DB;
use Mz\Models\Ipa\Field;
use Mz\Models\Ipa\FieldCategoryScore;
use Illuminate\Bus\Batchable;

class CalculateFieldScore implements ShouldQueue
{
    use Batchable, Dispatchable, InteractsWithQueue, Queueable, SerializesModels;

    private $category;
    private $field;

    public $timeout = 86400;

    public $backoff = 3;
    public $tries = 3;

    public function __construct(Category $category, Field $field)
    {
        $this->category = $category;
        $this->field = $field;
    }

    public function handle()
    {
        $fileIdsQuery = $this->getFileIdsQuery($this->category, $this->field);
        $avgCollection = $this->getAverageCollection($fileIdsQuery);

        FieldCategoryScore::updateOrCreate([
            'CategoryID' => $this->category->ID,
            'FieldID' => $this->field->ID
        ], [
            'AverageCollection' => $avgCollection,
            'Score' =>  DB::raw($this->getFieldCategoryScore($avgCollection, $this->category) ?? 'null')
        ]);
    }

    ...
}

Since the Category existed in CalculateCategoryScores and it was given in the constructor of CalculateFieldScore, how is it possible that the model is not found given that the table hasn't changed for more than a year? Also, note that it is only attempted 1 times, even if I set the $tries to 3.

naghal
  • 537
  • 3
  • 19

0 Answers0