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

WordPress Cron周五异常:缺失计划/触发过频,WooCommerce订单克隆失效

WooCommerce每周重复订单Cron故障分析与修复

问题根源

  1. 自定义Cron调度注册失效:WordPress更新后,everyweek调度的注册时机被打乱,系统无法识别这个自定义调度,触发“Cron missing schedule”错误。
  2. 对象参数传递不可靠:直接把WC_Order对象传给Cron任务是错误的——WordPress存储Cron任务时会序列化参数,但对象序列化后无法完整还原为有效WC_Order实例,执行时就会出现订单ID为0的情况,且WordPress会因任务失败自动每2分钟重试,造成频繁触发。
  3. 旧无效任务残留:更新前创建的错误Cron任务(带无效对象参数)未被清理,持续引发异常。

修复步骤

1. 确保自定义Cron调度正确注册

把调度注册逻辑绑定到init钩子,保证WordPress启动时就加载这个自定义调度:

// 在WordPress初始化阶段注册每周调度
add_action('init', function() {
    add_filter('cron_schedules', 'cron_add_weekly');
});

function cron_add_weekly( $schedules ) {
    $schedules['everyweek'] = array(
        'interval' => 60 * 60 * 24 * 7, // 每周总秒数
        'display' => __( 'Once Every Week' )
    );
    return $schedules;
}

2. 修改Cron参数传递逻辑(用订单ID替代对象)

Cron任务不能可靠传递对象,改用订单ID作为参数,在触发函数中重新获取订单实例:

修改激活函数:

add_action('woocommerce_order_action_clone_order_weekly', 'cronstarter_activation_weekly');
function cronstarter_activation_weekly( $order ) {
    if ( ! is_a($order, 'WC_Order') ) {
        return;
    }

    $order_id = $order->get_id();
    // 只传订单ID,避免对象序列化问题
    $args = array( $order_id );

    // 避免重复创建相同任务
    if( ! wp_next_scheduled( 'clone_order_weekly', $args ) ) {
        wp_schedule_event(time(), 'everyweek', 'clone_order_weekly', $args );
    }
}

修改触发函数:

add_action('clone_order_weekly', 'trigger_action_clone_order', 10, 1); // 明确声明接收1个参数
function trigger_action_clone_order( $order_id ) {
    // 通过ID重新获取订单对象
    $order = wc_get_order( $order_id );
    if ( ! is_a($order, 'WC_Order') || $order->get_order_number() == 0 ) {
        // 删除无效的Cron任务,避免重复触发错误
        wp_unschedule_event( wp_next_scheduled( 'clone_order_weekly', array($order_id) ), 'clone_order_weekly', array($order_id) );
        return;
    }

    // 测试邮件(可保留或删除)
    $recipients = 'myemail@someemail.com';
    $subject = 'Scheduled Cron Job from Order number #'.$order->get_order_number();
    $message = 'This is a test mail from a scheduled Cron Job on Order number #'.$order->get_order_number();
    wp_mail($recipients, $subject, $message);

    // 更新父订单的元数据标记
    $order->update_meta_data( '_is_recurring_order', 'true');
    $order->update_meta_data( '_is_recurring_order_weekly_parent', 'true');
    $order->update_meta_data( '_is_recurring_order_child_created', date("d-m-Y H:i:s"));
    $order->save();

    // 执行克隆逻辑
    $child_order = mutiara_woocommerce_order_clone( $order_id, 'everyweek');

    if ( $child_order && is_a($child_order, 'WC_Order') ) {
        $child_order_id = $child_order->get_id();
        $order->update_meta_data( '_recurring_order_child_id', $child_order_id );
        $order->save();
    }
}

3. 清理旧的无效Cron任务

把下面的代码临时添加到主题的functions.php,登录后台执行一次,清理所有旧的错误任务:

add_action('admin_init', function() {
    $crons = _get_cron_array();
    foreach ( $crons as $timestamp => $hooks ) {
        if ( isset( $hooks['clone_order_weekly'] ) ) {
            foreach ( $hooks['clone_order_weekly'] as $hash => $cron ) {
                wp_unschedule_event( $timestamp, 'clone_order_weekly', $cron['args'] );
            }
        }
    }
    wp_die('旧Cron任务已清理,请返回后台');
});

执行完成后,记得删除这段代码。

4. 重新激活订单克隆任务

清理完旧任务后,回到对应订单页面,重新点击激活每周克隆的按钮,创建新的有效Cron任务。

内容的提问来源于stack exchange,提问作者iv444

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.14 22:35:01