laravel 10调度任务本身不缓存,但可在任务内部用缓存实现结果复用、分布式锁防重、状态控制跳过:一、缓存产出物(如pdf路径)避免重复生成;二、用cache::lock()实现跨服务器互斥执行;三、用缓存键标记禁用或上次执行时间以动态跳过任务。

Laravel 10 本身不提供“任务缓存”这一内置概念。调度器(Schedule)负责定义定时任务的执行频率和触发逻辑,而缓存(Cache)是独立的数据存储机制,用于暂存查询结果、计算值等。两者职责不同:
- 调度器控制「什么时候运行命令」;
- 缓存控制「要不要重复查数据库或调 API」。
但你在实际开发中常会遇到这类需求:
✅ 某个调度任务(如 report:generate)每次执行都查库+渲染 PDF,耗时长;
✅ 希望它只在真正需要时才生成,其余时间直接返回已缓存的结果;
✅ 或者避免同一任务在多台服务器上被重复触发(即“分布式锁”式防重)。
这其实不是“给任务设缓存”,而是在任务内部用缓存做结果复用或执行协调。以下是三种典型、实用的做法:
一、用缓存存储任务结果,避免重复计算
适合:生成报表、统计汇总、API聚合类任务。
// app/Console/Commands/ReportGenerateCommand.php
public function handle()
{
$cacheKey = 'daily_report_pdf_' . now()->format('Y-m-d');
// 先尝试从缓存读取
if ($pdfPath = Cache::get($cacheKey)) {
$this->info("Report served from cache: {$pdfPath}");
return;
}
// 否则生成新报告(耗时操作)
$pdfPath = $this->generateDailyReport();
// 写入缓存,有效期24小时
Cache::put($cacheKey, $pdfPath, 3600 * 24);
$this->info("New report generated and cached: {$pdfPath}");
}
✅ 关键点:缓存的是任务产出物(路径、JSON、HTML 等),不是任务本身;TTL 根据业务新鲜度设定(如日报设 24h,实时监控设 60s)。
二、用缓存实现任务执行互斥(单机/简单分布式防重)
适合:清理脚本、同步任务等不允许并发执行的场景。
protected function schedule(Schedule $schedule)
{
$schedule->command('sync:orders')
->everyFiveMinutes()
->withoutOverlapping(); // Laravel 内置防重(基于文件锁)
}
但 withoutOverlapping() 默认用 file 驱动,跨服务器无效。升级为 Redis 锁更可靠:
// 在命令 handle() 开头加
$lockKey = 'lock:sync:orders';
if (! Cache::lock($lockKey, 300)->block(0)) { // 最多等 0 秒,不阻塞
$this->warn('Sync already running, skipped.');
return;
}
try {
// 执行同步逻辑...
$this->info('Sync started.');
} finally {
Cache::lock($lockKey)->release();
}
✅ 关键点:
Cache::lock()依赖底层驱动(推荐 Redis),自动处理加锁/释放/过期,比手写Cache::has()+Cache::put()更安全。
三、用缓存标记任务状态,支持手动触发与跳过
适合:运维类任务(如备份、归档),需人工干预或按条件跳过。
public function handle()
{
// 检查是否被手动禁用
if (Cache::has('disable:backup:full')) {
$this->warn('Full backup disabled via cache flag.');
return;
}
// 检查上次成功执行时间,避免太频繁
$lastRun = Cache::get('last_backup_time');
if ($lastRun && now()->diffInHours($lastRun) info('Skip: full backup ran less than 24h ago.');
return;
}
// 执行备份...
$this->performFullBackup();
// 更新状态
Cache::put('last_backup_time', now(), 3600 * 48); // 缓存48小时
}
✅ 关键点:把缓存当轻量配置中心或状态寄存器,灵活控制任务行为,无需改代码、发版。
不复杂但容易忽略。











