Use a Generator for job list to fix background-job:list commandtags/v26.0.0beta1
} | } | ||||
protected function execute(InputInterface $input, OutputInterface $output): int { | protected function execute(InputInterface $input, OutputInterface $output): int { | ||||
$jobs = $this->jobList->getJobs($input->getOption('class'), (int)$input->getOption('limit'), (int)$input->getOption('offset')); | |||||
$jobs = $this->jobList->getJobsIterator($input->getOption('class'), (int)$input->getOption('limit'), (int)$input->getOption('offset')); | |||||
$this->writeTableInOutputFormat($input, $output, $this->formatJobs($jobs)); | $this->writeTableInOutputFormat($input, $output, $this->formatJobs($jobs)); | ||||
return 0; | return 0; | ||||
} | } | ||||
protected function formatJobs(array $jobs): array { | |||||
return array_map( | |||||
fn ($job) => [ | |||||
protected function formatJobs(iterable $jobs): array { | |||||
$jobsInfo = []; | |||||
foreach ($jobs as $job) { | |||||
$jobsInfo[] = [ | |||||
'id' => $job->getId(), | 'id' => $job->getId(), | ||||
'class' => get_class($job), | 'class' => get_class($job), | ||||
'last_run' => date(DATE_ATOM, $job->getLastRun()), | 'last_run' => date(DATE_ATOM, $job->getLastRun()), | ||||
'argument' => json_encode($job->getArgument()), | 'argument' => json_encode($job->getArgument()), | ||||
], | |||||
$jobs | |||||
); | |||||
]; | |||||
} | |||||
return $jobsInfo; | |||||
} | } | ||||
} | } |
return (bool) $row; | return (bool) $row; | ||||
} | } | ||||
/** | |||||
* get all jobs in the list | |||||
* | |||||
* @return IJob[] | |||||
* @deprecated 9.0.0 - This method is dangerous since it can cause load and | |||||
* memory problems when creating too many instances. Use getJobs instead. | |||||
*/ | |||||
public function getAll(): array { | |||||
return $this->getJobs(null, null, 0); | |||||
public function getJobs($job, ?int $limit, int $offset): array { | |||||
$iterable = $this->getJobsIterator($job, $limit, $offset); | |||||
if (is_array($iterable)) { | |||||
return $iterable; | |||||
} else { | |||||
return iterator_to_array($iterable); | |||||
} | |||||
} | } | ||||
/** | /** | ||||
* @param IJob|class-string<IJob>|null $job | * @param IJob|class-string<IJob>|null $job | ||||
* @return IJob[] | |||||
* @return iterable<IJob> Avoid to store these objects as they may share a Singleton instance. You should instead use these IJobs instances while looping on the iterable. | |||||
*/ | */ | ||||
public function getJobs($job, ?int $limit, int $offset): array { | |||||
public function getJobsIterator($job, ?int $limit, int $offset): iterable { | |||||
$query = $this->connection->getQueryBuilder(); | $query = $this->connection->getQueryBuilder(); | ||||
$query->select('*') | $query->select('*') | ||||
->from('jobs') | ->from('jobs') | ||||
$result = $query->executeQuery(); | $result = $query->executeQuery(); | ||||
$jobs = []; | |||||
while ($row = $result->fetch()) { | while ($row = $result->fetch()) { | ||||
$job = $this->buildJob($row); | $job = $this->buildJob($row); | ||||
if ($job) { | if ($job) { | ||||
$jobs[] = $job; | |||||
yield $job; | |||||
} | } | ||||
} | } | ||||
$result->closeCursor(); | $result->closeCursor(); | ||||
return $jobs; | |||||
} | } | ||||
/** | /** | ||||
* get the next job in the list | |||||
* Get the next job in the list | |||||
* @return ?IJob the next job to run. Beware that this object may be a singleton and may be modified by the next call to buildJob. | |||||
*/ | */ | ||||
public function getNext(bool $onlyTimeSensitive = false): ?IJob { | public function getNext(bool $onlyTimeSensitive = false): ?IJob { | ||||
$query = $this->connection->getQueryBuilder(); | $query = $this->connection->getQueryBuilder(); | ||||
} | } | ||||
} | } | ||||
/** | |||||
* @return ?IJob The job matching the id. Beware that this object may be a singleton and may be modified by the next call to buildJob. | |||||
*/ | |||||
public function getById(int $id): ?IJob { | public function getById(int $id): ?IJob { | ||||
$row = $this->getDetailsById($id); | $row = $this->getDetailsById($id); | ||||
* get the job object from a row in the db | * get the job object from a row in the db | ||||
* | * | ||||
* @param array{class:class-string<IJob>, id:mixed, last_run:mixed, argument:string} $row | * @param array{class:class-string<IJob>, id:mixed, last_run:mixed, argument:string} $row | ||||
* @return ?IJob the next job to run. Beware that this object may be a singleton and may be modified by the next call to buildJob. | |||||
*/ | */ | ||||
private function buildJob(array $row): ?IJob { | private function buildJob(array $row): ?IJob { | ||||
try { | try { |
public function has($job, $argument): bool; | public function has($job, $argument): bool; | ||||
/** | /** | ||||
* get all jobs in the list | |||||
* Get jobs matching the search | |||||
* | * | ||||
* @return IJob[] | |||||
* @since 7.0.0 | |||||
* @deprecated 9.0.0 - This method is dangerous since it can cause load and | |||||
* memory problems when creating too many instances. Use getJobs instead. | |||||
* @param IJob|class-string<IJob>|null $job | |||||
* @return array<IJob> | |||||
* @since 25.0.0 | |||||
* @deprecated 26.0.0 Use getJobsIterator instead to avoid duplicated job objects | |||||
*/ | */ | ||||
public function getAll(): array; | |||||
public function getJobs($job, ?int $limit, int $offset): array; | |||||
/** | /** | ||||
* Get jobs matching the search | * Get jobs matching the search | ||||
* | * | ||||
* @param IJob|class-string<IJob>|null $job | * @param IJob|class-string<IJob>|null $job | ||||
* @return IJob[] | |||||
* @since 25.0.0 | |||||
* @return iterable<IJob> | |||||
* @since 26.0.0 | |||||
*/ | */ | ||||
public function getJobs($job, ?int $limit, int $offset): array; | |||||
public function getJobsIterator($job, ?int $limit, int $offset): iterable; | |||||
/** | /** | ||||
* get the next job in the list | * get the next job in the list |
return $this->jobs; | return $this->jobs; | ||||
} | } | ||||
public function getJobs($job, ?int $limit, int $offset): array { | |||||
public function getJobsIterator($job, ?int $limit, int $offset): array { | |||||
if ($job instanceof IJob) { | if ($job instanceof IJob) { | ||||
$jobClass = get_class($job); | $jobClass = get_class($job); | ||||
} else { | } else { |
} | } | ||||
protected function getAllSorted() { | protected function getAllSorted() { | ||||
$jobs = $this->instance->getAll(); | |||||
$iterator = $this->instance->getJobsIterator(null, null, 0); | |||||
$jobs = []; | |||||
foreach ($iterator as $job) { | |||||
$jobs[] = clone $job; | |||||
} | |||||
usort($jobs, function (IJob $job1, IJob $job2) { | usort($jobs, function (IJob $job1, IJob $job2) { | ||||
return $job1->getId() - $job2->getId(); | return $job1->getId() - $job2->getId(); |