我们知道,WooCommerce中有很多Hook,在开发WooCommerce主题或插件时,要找出把自定义功能挂载到哪个Hook上面有时候会比较困难。在本文中,我将带大家一起来了解一下WooCommerce订单生命周期中会出现的Hook。
通过前端结账过程中创建的订单
WooCommerce目前有两种版本的结账页面,一种是通过短代码创建的经典结账页面,一种是通过区块创建的,这两种类型的结账页面中所触发的Hooks有一些区别,请注意区分。
经典结帐过程中的Hooks
如果您的商店结账页面是使用如下图所示的方式创建的,那么您的结账页面就是经典结账页面。在WooCommerce8.3 以前的版本中,WooCommerce会自动使用 woocommerce_checkout
短代码创建经典结账页面。
经典结账页面中,结账过程中所触发的Hooks 如下:
- woocommerce_checkout_create_order:在保存订单之前。
- woocommerce_new_order:保存订单及其自定义字段数据之后。
- woocommerce_checkout_order_created:保存订单及其自定义字段数据之后。
- woocommerce_checkout_order_processed:订单成功创建之后、处理付款之前,有点类似于前面两个Hook,不同的是此Hook在订单创建失败后也会被触发。
- 订单状态发生改变的Hooks :改变为处理中。
- woocommerce_payment_complete:完成付款时,但订单状态为“暂停”、“待处理”、“失败”、“已取消”(可以使用过滤器更改)。
- woocommerce_thankyou:这实际上是您应该避免使用的Hook,因为根据付款方式,并非每个人都在“谢谢”页面上完成。
区块结帐过程中的Hooks
WooCommerce8.3版本之后,WooCommerce会默认使用区块方法创建结账页面,越来越多的 WooCommerce 商店开始使用这种方式创建结账页面了。
使用区块方式创建的结账页面和经典结账页面中所触发的Hooks有很大不同,下面是使用区块方式创建的结账页面中所触发的Hooks:
- woocommerce_new_order
- woocommerce_update_order
- woocommerce_store_api_checkout_order_processed
- 订单状态发生改变的Hooks :从draft到pending
- 再次触发订单状态发生改变的Hooks:从pending到processing
- woocommerce_payment_complete
- woocommerce_thankyou
woocommerce_update_order
这里可以被触发大约 5 次。在WooCommerce后台手动创建或更新的订单
如果您以前使用过类似save_post或 save_post_shop_order Hooks,建议您停止这样做,因为这些Hooks是为常规 WordPress 自定义文章类型而不是为 WooCommerce 订单设计的,更重要的是,它们不适用于高性能存储数据类型的订单。
我们需要的Hook是:
- woocommerce_new_order
- woocommerce_update_order:会被触发多次
这里的主要问题是——有没有办法区分这些Hook是从 WordPress 仪表板还是从其他地方触发的?很简单——只需检查随机数即可!
add_action( 'woocommerce_new_order', 'wprs_create_or_update_order', 25, 2 );
add_action( 'woocommerce_update_order', 'wprs_create_or_update_order', 25, 2 );
function wprs_create_or_update_order( $order_id, $order ) {
if(
isset( $_REQUEST[ '_wpnonce' ] )
&& wp_verify_nonce( $_REQUEST[ '_wpnonce' ], "update-order_{$order_id}" )
) {
// do your stuff
}
}
除了 nonce 方式,我们也可以使用 check_admin_referer()
来进行检查。
删除订单之后触发的Hooks
当我们删除订单时,只会触发两个Hook,具体是哪一个取决于您是永久删除订单还是只是将其移至垃圾箱。
- woocommerce_before_delete_order或woocommerce_before_trash_order
- woocommerce_delete_order或woocommerce_trash_order
如果您正在使用这些Hooks之一,并且需要检查它是否是从 WordPress 管理仪表板触发的,您可以像这样验证随机数:
add_action('woocommerce_before_trash_order', function ($order_id)
{
if (isset($_REQUEST[ '_wpnonce' ]) && wp_verify_nonce($_REQUEST[ '_wpnonce' ], 'bulk-orders')) {
// do your stuff
}
});
通过 REST API 创建或更新订单时触发的Hooks
通过 WooCommerce REST API 创建或更新订单时。我们可以使用的Hooks有:
- woocommerce_new_order
- woocommerce_update_order:会被触发多次
- 所有订单状态发生改变的Hooks :从pending到processing
- woocommerce_payment_complete
由于我们没有专门用于 REST API 请求的Hook,我们是否可用某种方式区分某Hook是由 REST API 请求触发还是以其他方式触发?可以的,我们只需要检查REST_REQUEST函数中的常量即可。
add_action( 'woocommerce_new_order', 'wprs_create_or_update_order_restapi' );
add_action( 'woocommerce_update_order', 'wprs_create_or_update_order_restapi' );
function wprs_create_or_update_order_restapi( $order_id ) {
if( defined( 'REST_REQUEST' ) ) {
// do your stuff
}
}
订单状态发生改变时的Hooks
WooCommerce 中的订单状态可以经常更改,这就是为什么您会在本教程的几乎所有其他章节中看到指向本章的链接。
订单状态变化时触发的Hook:
- woocommerce_update_order
- woocommerce_order_status_{$status_from}_to_{$status_to}
- woocommerce_order_status_changed
第二个Hook允许我们提供更改前的和更改后订单状态名称作为Hook名称的一部分,第三个Hook无论如何都可以将订单状态名称用作函数参数。
订单退款之后触发的Hooks
最后是 WooCommerce 订单发生退款时触发的Hook。
- woocommerce_order_fully_refunded或woocommerce_order_partially_refunded
- 订单状态发生改变的Hooks:从当前状态变为refunded
- woocommerce_update_order
- woocommerce_order_refunded