diff --git a/src/Schedule/Infrastructure/Drivers/LaravelQueueDriver.php b/src/Schedule/Infrastructure/Drivers/LaravelQueueDriver.php index c7bca8a3..db80fc6b 100644 --- a/src/Schedule/Infrastructure/Drivers/LaravelQueueDriver.php +++ b/src/Schedule/Infrastructure/Drivers/LaravelQueueDriver.php @@ -49,11 +49,27 @@ public function available(): bool public function placeIdentified(Event $event): bool { - $this->send(RunScheduledEvent::for($event)); + $this->send(RunScheduledEvent::for($this->withInterval($event))); return true; } + /** + * A recurring event runs again only when its job knows the interval: the fluent API and #[Schedule] give the name of the recurrence, WordPress's own functions give both. + */ + private function withInterval(Event $event): Event + { + if ($event->recurrence === null || $event->interval !== null) { + return $event; + } + + $interval = (int) ((function_exists('wp_get_schedules') ? wp_get_schedules() : [])[$event->recurrence]['interval'] ?? 0); + + return $interval > 0 + ? new Event($event->hook, $event->timestamp, $event->recurrence, $event->args, $interval, $event->driver, $event->id) + : $event; + } + public function once(string $hook, int $timestamp, array $args = []): bool { return $this->place(new Event($hook, $timestamp, null, $args)); @@ -61,9 +77,7 @@ public function once(string $hook, int $timestamp, array $args = []): bool public function recurring(string $hook, int $timestamp, string $recurrence, array $args = []): bool { - $interval = (int) ((function_exists('wp_get_schedules') ? wp_get_schedules() : [])[$recurrence]['interval'] ?? 0); - - return $this->place(new Event($hook, $timestamp, $recurrence, $args, $interval > 0 ? $interval : null)); + return $this->place($this->withInterval(new Event($hook, $timestamp, $recurrence, $args))); } /** diff --git a/tests/Feature/Schedule/LaravelDriverTest.php b/tests/Feature/Schedule/LaravelDriverTest.php index 298e29b5..38d56645 100644 --- a/tests/Feature/Schedule/LaravelDriverTest.php +++ b/tests/Feature/Schedule/LaravelDriverTest.php @@ -138,6 +138,21 @@ function dispatchedJobs(): array ->and($this->engine->next('digest', ['u' => 1]))->toBeNull(); }); + it('gives a recurring event the interval of its recurrence when the caller gave none: the fluent API and #[Schedule] only know the name', function (): void { + $this->engine->place(new Event('reports', time() - 5, 'daily', [])); + + expect(dispatchedJobs()[0]->interval)->toBe(86400); + + $job = dispatchedJobs()[0]; + $job->handle($this->driver); + + $next = CronIndex::events('laravel'); + + expect($next)->toHaveCount(1) + ->and($next[0]->hook)->toBe('reports') + ->and($next[0]->timestamp)->toBe($job->timestamp + 86400); + }); + it('stores a single event of the WordPress functions the same way', function (): void { $this->driver->once('digest', time() + 600, []); $this->driver->recurring('reports', time() + 600, 'daily', []);