I’m using the most recent versions of WordPress and WooCommerce.
I’m aware this might seem weird out of context, but I wanna add a hook to my functions.php that removes a certain product by ID from an order after the order has been placed.
Here is what I am working with so far:
add_action('woocommerce_new_order', 'custom_process_order', 10, 1);
function custom_process_order($order_id) {
$order = new WC_Order( $order_id );
$items = $order->get_items();
foreach ($items as $item) {
if ($item->get_id()==10766) {
$order->remove_item( $item->get_id() );
}
}
return $order_id;
}
I am trying to remove the product with the ID 10766 from the order if said product is part of the order.
I took this from a different, older post here so the code itself might not be perfect. It definitely isn’t working.
Update after some experimentation:
With the help of Cameron Hurd, I tried the following code:
add_action('woocommerce_new_order', 'custom_process_order', 10, 1);
function custom_process_order($order_id) {
$order = new WC_Order( $order_id );
$items = $order->get_items();
foreach ($items as $item) {
if ($item->get_id() === 10766) {
$order->remove_item( $item->get_id() );
}
}
$order->save_items();
return $order_id;
}
This seemed promising, but pressing the checkout button will submit an empty order while also throwing an empty WooCommerce error message leaving the user on the checkout page.
After this I had 2 ideas:
1.) Changing remove_item
to wc_delete_order_item
. I really don’t know the difference and changing it didn’t seem to make a difference either.
2.) Changing the hook so it happens after the order is in the back end. I tried changing it from woocommerce_new_order
to woocommerce_thankyou
. This however broke the thank you page in addition to doing nothing to the order.
This is what I’m sitting with now:
add_action('woocommerce_checkout_create_order', 'custom_process_order', 10, 1);
function custom_process_order($order_id) {
$order = new WC_Order( $order_id );
$items = $order->get_items();
foreach ($items as $item) {
$current_item_id = $item->get_id();
if ( $current_item_id === 10766) {
$order->remove_item($current_item_id);
}
}
$order->save_items();
return $order_id;
}
Still looking for a working answer.
2
Answers
Browsing the code from
abstracts/abstract-wc-order.php
, where theremove_item
method is located… I see that items are added to an array calleditems_to_delete
. That variable shows up again insave_items
, where each item class to be deleted has itsdelete
method invoked.Therefore, you might try calling
$order->save_items()
after the foreach loop in your custom action:You could use the
woocommerce_checkout_order_processed
action hook,where you then specify the product id.
So you get: