Encodera

Спасибо, что читаете!

Пожертвуйте сайту, мы стараемся ради вас.

Оглавление

Планировщик задач

Очистить старые записи ночью, раз в час обновить курсы валют, по понедельникам отправить отчёт — такие задачи выполняются по расписанию. Обычно для каждой добавляют строку в cron на сервере. В Laravel расписание описано в коде проекта, а на сервере нужна всего одна запись.

Расписание

Задачи описывают в файле routes/console.php:

use Illuminate\Support\Facades\Schedule;
 
Schedule::command('reports:send')->weeklyOn(1, '9:00');
 
Schedule::command('model:prune')->daily();

Первая строка запускает команду Artisan по понедельникам в девять утра, вторая — каждый день в полночь.

Что можно запланировать

use App\Jobs\UpdateExchangeRates;
use Illuminate\Support\Facades\DB;
 
Schedule::job(new UpdateExchangeRates)->hourly();
 
Schedule::call(function () {
    DB::table('sessions')->where('last_activity', '<', now()->subWeek()->timestamp)->delete();
})->daily();
 
Schedule::exec('node /var/www/scripts/report.js')->monthly();

job() отправляет задание в очередь, call() выполняет функцию, exec() — команду операционной системы.

Частота

МетодКогда выполняется
everyMinute()Каждую минуту
everyFiveMinutes()Каждые пять минут
hourly()В начале каждого часа
daily()Каждый день в полночь
dailyAt('13:00')Каждый день в указанное время
weekly()Раз в неделю
monthly()Первого числа каждого месяца
cron('0 */6 * * *')По выражению cron

Ограничения

Schedule::command('emails:send')
    ->weekdays()
    ->between('8:00', '18:00')
    ->timezone('Europe/Moscow');
 
Schedule::command('backup:run')
    ->daily()
    ->environments(['production']);

Защита от наложения

Если задача выполняется дольше, чем интервал между запусками, следующий запуск начнётся поверх предыдущего. withoutOverlapping() этого не допускает:

Schedule::command('import:products')
    ->everyFiveMinutes()
    ->withoutOverlapping();

На сайте с несколькими серверами добавляют onOneServer(), чтобы задача выполнилась только на одном.

Запуск на сервере

В cron сервера добавляют единственную строку. Она каждую минуту вызывает планировщик, а тот сам решает, что пора выполнить:

* * * * * cd /var/www/blog && php artisan schedule:run >> /dev/null 2>&1

Проверка

php artisan schedule:list
php artisan schedule:work

Первая команда показывает все задачи и время следующего запуска. Вторая запускает планировщик в терминале — так расписание проверяют при разработке, без настройки cron.

Частая ошибка

Время в расписании считается в часовом поясе приложения — по умолчанию это UTC. Задача dailyAt('9:00') выполнится в девять утра по Гринвичу, то есть в полдень по Москве. Укажите пояс в настройке timezone файла config/app.php или методом timezone() у самой задачи.

Спасибо, что читаете!

Пожертвуйте сайту, мы стараемся ради вас.