thinkphp 6.0 的 think-queue 扩展要求任务类必须定义 fire(job $job, $data) 方法作为唯一入口,不可使用 laravel 风格的 handle();发布任务需传类名字符串如 'app\job\sendemailjob',执行成功必须显式调用 $job->delete() 否则会重复消费。

任务类必须有 fire 方法,不是 handle
ThinkPHP 6.0 的 topthink/think-queue 扩展(非 Laravel 风格)要求任务类必须实现 fire(Job $job, $data) 方法,而不是 Laravel 风格的 handle()。很多开发者照搬 Laravel 写法,结果任务静默失败、无日志、不报错,只因方法名不对。
-
fire()是唯一被队列监听器识别的入口,handle()完全不会被调用 - 若想复用逻辑,可在
fire()中调用私有方法,但不能删掉fire - 多任务场景下(如一个类里有多个业务),仍需统一走
fire,再根据$data分支处理
Queue::push() 的第一个参数是类名字符串,不是实例
发布任务时,Queue::push() 第一个参数必须是完整命名空间的类名字符串(如 'app\job\SendEmailJob'),不是对象实例,也不是带 @method 的写法(那是旧版或自定义封装)。
- 错误写法:
Queue::push(new SendEmailJob(), $data)→ 报错或序列化失败 - 错误写法:
Queue::push('app\job\SendEmailJob@send')→ 仅在部分自定义驱动中支持,原生redis或database驱动不识别该语法 - 正确写法:
Queue::push('app\job\SendEmailJob', $data, 'email'),第三个参数是队列名(可选,默认default)
任务执行完必须手动删除,否则会重复消费
fire() 方法内部**不会自动标记完成**。哪怕逻辑跑通了,只要没调用 $job->delete(),这个任务就会被反复取出重试(尤其在 Redis 驱动下,retry_after 超时后会重新入队)。
- 成功路径必须显式调用:
$job->delete() - 失败路径建议调用:
$job->fail()或$job->release($delay)(延时重试) - 常见漏写点:异常捕获后只
log了,忘了fail(),导致任务卡在队列里不断重试
Redis 驱动下,queue 配置项实际决定 Redis key 前缀
在 config/queue.php 的 redis 连接配置中,'queue' => 'default' 并不只是个名字,它会作为 Redis List key 的前缀,最终生成类似 queues:default 的键名。如果你改了这个值,但没同步更新 php think queue:listen --queue xxx 的命令参数,就会监听错队列,任务“发出去了却没人收”。
- 比如配成
'queue' => 'sms',就必须用php think queue:listen --queue sms - 多个业务共用 Redis 实例时,靠这个
queue值做逻辑隔离,别和数据库表名混淆 - 该值不支持路径或特殊字符,建议只用小写字母+下划线
$job->delete() 调用时机——它不在框架自动兜底范围内,写错位置(比如放在 try 外面)、漏写、或只写在 success 分支而忽略 catch 后的清理,都会让队列堆积或无限重试。php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











