gotchaphplaravelMajor
Laravel Task Scheduling: Preventing Overlapping and Running on Multiple Servers
Viewed 0 times
schedulingwithoutOverlappingonOneServercronrace conditionlockmulti-servertask
Problem
A scheduled task takes longer than its interval to complete. On the next invocation a second instance starts, causing duplicate work, data corruption, or race conditions. On multi-server deployments every server runs every task.
Solution
Chain ->withoutOverlapping() to prevent concurrent runs. Chain ->onOneServer() to ensure only one server in a multi-server setup executes the task. Both require the cache driver to support atomic locks (Redis recommended). Add ->runInBackground() for tasks that should not block the scheduler process.
Why
The scheduler runs as a single cron calling php artisan schedule:run every minute. Without withoutOverlapping() there is no coordination between invocations. onOneServer() uses an atomic lock to elect one server per minute.
Gotchas
- withoutOverlapping() defaults to a 24-hour lock expiry; pass minutes: ->withoutOverlapping(10)
- onOneServer() requires a shared cache backend across all servers
- Scheduled closures cannot use onOneServer() or withoutOverlapping()—use artisan commands instead
- Use ->before() and ->after() hooks for pre/post task logging
Code Snippets
Scheduled command with overlap and server guards
$schedule->command('reports:generate')
->hourly()
->withoutOverlapping()
->onOneServer()
->runInBackground();Revisions (0)
No revisions yet.