Laravel Task Scheduling: Cron Automation & Background Daemons

In traditional server administration, automating repetitive tasks (daily database backups, hourly currency exchange updates, weekly newsletter dispatching) required logging into your Linux terminal via SSH and configuring multiple confusing crontab entries. In Laravel, you configure a single master cron entry on your server, and manage all schedules directly in clean, version-controlled PHP code.

1. The Single Server Crontab Entry

On your production Linux server, execute crontab -e and add this single line:

* * * * * cd /path-to-your-project && php artisan schedule:run >> /dev/null 2>&1

This cron entry evaluates every single minute. It invokes Laravel's scheduler, which inspects your scheduled tasks and executes whichever jobs are due!

2. Defining Schedules in routes/console.php

In Laravel 11, define scheduled tasks in routes/console.php using the Schedule facade:

use Illuminate\Support\Facades\Schedule;

// 1. Schedule a custom Artisan command to run every Monday at 8:00 AM
Schedule::command('report:weekly-digest')
    ->weeklyOn(1, '08:00')
    ->withoutOverlapping() // Uses Redis cache lock to prevent concurrent overlaps!
    ->emailOutputOnFailure('devops@veewom.com');

// 2. Schedule a Queued Job to run every 15 minutes during business hours
Schedule::job(new \App\Jobs\SyncStockInventory)
    ->everyFifteenMinutes()
    ->weekdays()
    ->between('09:00', '18:00');

// 3. Schedule a simple PHP closure every night at midnight
Schedule::call(function () {
    \App\Models\UserCart::where('updated_at', '<', now()->subDays(30))->delete();
})->dailyAt('00:00');

3. Common Schedule Frequency Options

Frequency Method Execution Timing
->everyMinute() Runs every 60 seconds
->hourly() / ->hourlyAt(15) Runs once an hour (or at 15 minutes past the hour)
->daily() / ->dailyAt('13:00') Runs once a day at 1:00 PM
->weekly() / ->monthly() Runs once a week or once a month
->onOneServer() Executes on only ONE server across a multi-server cluster

Frequently Asked Questions (FAQ) - Student & Interview Review

Q1. What does the withoutOverlapping() method do?

If a scheduled task takes longer to execute than its frequency interval (e.g. a 5-minute task running every 2 minutes), withoutOverlapping uses an atomic cache lock to prevent a second instance from starting until the first finishes.

Q2. How can I test scheduled tasks locally without waiting for real time to elapse?

Run: 'php artisan schedule:work' in your terminal. This keeps a local process alive that executes the scheduler every minute for testing.

Q3. How does ->onOneServer() coordinate tasks across multiple servers?

It uses your centralized Redis or Memcached cache store to acquire an atomic mutex lock. The first server to acquire the lock executes the task, while other servers skip it.

Explore Related Laravel Tutorials & Next Steps

Broaden your backend architecture, REST API design, and enterprise production engineering expertise:

Artisan CLI & Custom Commands

Write custom Artisan commands to schedule inside routes/console.php.

Queues & Async Scheduled Jobs

Dispatch queued jobs from the scheduler to maintain instant execution intervals.

Atomic Locks & WithoutOverlapping

Prevent scheduled tasks from overlapping using Redis atomic cache locks.

Production Cron Server Setup

Configure * * * * * php /path/to/artisan schedule:run >> /dev/null 2>&1.

Share Share on Facebook Share on Twitter Share on LinkedIn Pin on Pinterest Share on Reddit

You may also like this!