You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Laravel Horizon清空队列报需调用redis.replicate_commands()问题咨询

环境组件版本信息
  • Horizon版本: 5.7
  • Laravel版本: 8.40
  • PHP版本: 7.4.22
  • Redis驱动及版本: predis/phpredis 3.2.12 & predis 1.1
  • 数据库驱动及版本: 未提供
问题描述

执行队列清空操作时触发如下报错:

ERR Error running script (call to f_281c23c60c642d42fdedcc1acc8adc7317dd75a5): @user_script:18: @user_script: 18: Write commands not allowed after non deterministic commands. Call redis.replicate_commands() at the start of your script in order to switch to single commands replication mode.

报错本质是Redis 3.2及以上版本的EVAL脚本安全限制:脚本中执行过非确定性命令(如SCAN)后,默认脚本复制模式下不允许再执行写命令,避免主从数据不一致。

复现步骤

执行以下Artisan命令即可触发:

php artisan horizon:clear --queue=supplier_feeds_queue
临时解决方案

当前可通过直接操作Redis删除对应队列Key:

redis-cli --scan --pattern *supplier_feeds_queue* | xargs redis-cli del
永久修复方案

不需要自行手动调用redis.replicate_commands(),可按以下两种方案处理:

方案1:升级Horizon版本

当前使用的Horizon 5.7属于存在该Bug的版本,官方已在后续5.x分支的补丁版本中修复了该问题,直接升级Horizon到5.x最新稳定版即可,该升级不会破坏现有功能兼容性。

方案2:重写队列清空逻辑

如果无法升级依赖,可通过继承重写Horizon的RedisQueue类修复:

  1. 新建app/Queue/HorizonRedisQueue.php文件,代码如下:
<?php

namespace App\Queue;

use Laravel\Horizon\RedisQueue as BaseRedisQueue;

class HorizonRedisQueue extends BaseRedisQueue
{
    public function clear($queue)
    {
        // 原Lua脚本第一行新增redis.replicate_commands()调用
        $lua = <<<'LUA'
redis.replicate_commands()
local cursor = "0"
local deleted = 0
repeat
    local results = redis.call('SCAN', cursor, 'MATCH', ARGV[1], 'COUNT', 1000)
    cursor = results[1]
    local keys = results[2]
    if #keys > 0 then
        deleted = deleted + redis.call('DEL', unpack(keys))
    end
until cursor == "0"
return deleted
LUA;

        return $this->getConnection()->eval($lua, 0, $this->getQueue($queue).'*');
    }
}
  1. 在app/Providers/AppServiceProvider.php的register方法中添加绑定,替换默认的RedisQueue实现:
$this->app->bind('horizon.queue', function () {
    return new \App\Queue\HorizonRedisQueue(
        $this->app['redis']->connection(config('horizon.connection'))
    );
});

修复后再执行php artisan horizon:clear命令就不会触发该报错。


内容的提问来源于stack exchange,提问作者David van der Tuijn

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.04 22:54:03