将 Woocommerce 订阅更新和同步到自定义日期

Updating and Synchronizing Woocommerce Subscriptions to Custom Date

我们有一个客户正在运送订阅产品(实际上是复合产品,其中有四到五个产品捆绑包),他们每周提供一次送货服务。他们的交货日期总是星期四。 Woocommerce 订阅允许同步到特定日期,因此我们选择了“对齐订阅续订日”选项,并且在给定的产品中,我们将每个选项设置为星期四(“每 4 周”,“每 3 周”等)

我们的情况需要注意的是,前一天(星期三)或星期四收到的订单无法在该周完成,需要 开始 date/delivery 日期 撞到了下个星期四。为此,我们使用 woocommerce_subscriptions_product_first_renewal_payment_time 钩子为 functions.php 编写了一个函数:

<?php
function rem_check_renewal_date( $first_renewal_timestamp, $product_id, $from_date_param, $timezone ) {

  if ( date('D') == 'Wed' || date('D') == 'Thu' ) {

    $from_date_param = strtotime('Thursday next week');
    return $from_date_param;

  } else {

    // Nothing needs to be done, because we must be on a Fri thru Tue
    return;

  }

}

add_filter( 'woocommerce_subscriptions_product_first_renewal_payment_time', 'rem_check_renewal_date', 10, 4);
?>

现在我们已经完成了,我们可以看到结账上的一些字段似乎正在正确更新。例如,在下次付款日期(我们将其更改为下次交货)下,它正确显示下周而不是今天(在撰写本文时恰好是星期四)。

但并非订阅仪表板中的所有 fields/columnar 值都已更改。例如,实际开始日期列显示收到订单的日期。

您还可以在 Woocommerce 发送的确认电子邮件中看到开始日期被列为当前日期,尽管根据我们的钩子,“下一次付款”被移动了一周。

当我们在星期三下测试订单时,“开始日期”列显示星期三。如果它的实际用途是作为“收到订单”日期,那是有道理的,所以我的问题是:

哪些(如果有)其他列 and/or 值需要更新,以便将前一天或交货当天收到的订单移至下周?​​我们需要确保后续订单保持在 2 周、3 周、4 周的时间表上,并与更改后的第一个付款日期保持一致。但我不确定仅使用上面的钩子更改第一个付款日期是否足够并且文档没有进一步详细说明。

WC_Subscription 对象公开了一个名为 update_dates() 的函数,它采用与订阅列表仪表板(和其他区域)中使用的值相匹配的日期键数组。

函数签名是WC_Subscription::update_dates( $dates, $timezone )。我相信一个对象必须被实例化;我不认为可以静态调用此方法。 Subscriptions function reference here.

记录的参数(作为要在 $dates 数组中传递的键)是:

  1. start
  2. trial_end
  3. next_payment
  4. last_payment
  5. end

数组本身是必需的,但我不认为每个单独的键都需要填充一个值。例如,订阅插件生成的默认订单通常没有 trial_endend 日期(除非以这种方式单独配置)。

使用诸如 woocommerce_checkout_subscription_created (Subscriptions action reference) 之类的操作挂钩,您可以使用 $subscription 参数,它是 WC_Subscription 的一个实例,并执行如下操作:

function push_subscriptions_to_next_week($subscription, $order, $recurring_cart) {
    // The new date calculation of +7 days is just an example
    $new_dates = array(
        'start' => date('Y-m-d H:i:s', strtotime('+7 days', time())),
        'next_payment' => date('Y-m-d H:i:s', strtotime('+7 days', time()))
    );

    $subscription->update_dates($new_dates, 'site');
}

add_action( 'woocommerce_checkout_subscription_created', 'push_subscriptions_to_next_week', 10, 3);

日期必须采用 MySQL date/time 格式 (Y-m-d H:i:s),因此我更新了代码示例以反映这一点。