phpwordpresswoocommercehook-woocommercewoocommerce-bookings

Change Woocommerce booking status on Custom Order Status change


I have some custom order statuses (made with WooCommerce Order Status Manager). But when I use a custom paid status, the booking status is not updated to "paid". I've cobbled together some code from various references but it results in a fatal error. Or maybe I am missing something where custom statuses are supposed to update the booking paid status without extra code?

My code:

add_action('woocommerce_order_status_pool-payment-rec','auto_change_booking_status_to_paid', 10, 1);
function auto_change_booking_status_to_paid($booking_id) {
    $booking = new WC_Booking( $booking_id );
    $order_id = $booking->get_order_id();
    $booking->update_status('paid', 'order_note');
    exit;
}

The error:

[20-Mar-2018 23:32:05 UTC] PHP Fatal error:  Uncaught Exception: Invalid booking. in /home/ahbc/public_html/wp-content/plugins/woocommerce-bookings/includes/data-stores/class-wc-booking-data-store.php:83
Stack trace:
#0 /home/ahbc/public_html/wp-content/plugins/woocommerce/includes/class-wc-data-store.php(149): WC_Booking_Data_Store->read(Object(WC_Booking))
#1 /home/ahbc/public_html/wp-content/plugins/woocommerce-bookings/includes/data-objects/class-wc-booking.php(149): WC_Data_Store->read(Object(WC_Booking))
#2 /home/ahbc/public_html/wp-content/plugins/ahbc-website-tweaks/ahbc-website-tweaks.php(104): WC_Booking->__construct(2223)
#3 /home/ahbc/public_html/wp-includes/class-wp-hook.php(288): auto_change_booking_status_to_paid(2223)
#4 /home/ahbc/public_html/wp-includes/class-wp-hook.php(310): WP_Hook->apply_filters('', Array)
#5 /home/ahbc/public_html/wp-includes/plugin.php(453): WP_Hook->do_action(Array)
#6 /home/ahbc/public_html/wp-content/plugins/woocommerce/includes/class-wc-order.php(327): do_action('woocommerce_ord...', 2223, Object(WC_Order))
# in /home/ahbc/public_html/wp-content/plugins/woocommerce-bookings/includes/data-stores/class-wc-booking-data-store.php on line 83

I've also tried this but it seemingly does nothing:

function sv_wc_order_statuses_needs_payment( $statuses, $order ) {
    // use your custom order status slug here
    $statuses[] = 'pool-payment-rec';
    return $statuses;
}
add_filter( 'woocommerce_valid_order_statuses_for_payment_complete', 'sv_wc_order_statuses_needs_payment', 10, 2 );

My references:

woocommerce booking status changes woocommerce order status

Change Woocommerce order status for Cash on delivery

https://gist.github.com/bekarice/e922e79bc40eb0729095abc561cfe621

EDIT: Have also tried several variations on the following:

add_action( 'woocommerce_order_status_changed', 'auto_change_booking_status_to_paid' );

function auto_change_booking_status_to_paid( $order_id ) {
    if( ! $order_id ) return;   

    $order = wc_get_order($order_id);
    $booking = get_wc_booking($booking_id);

    if( $order->get_status() == 'test' )
//  $order_id = $booking->get_order_id();
    $booking->update_status('confirmed', 'order_note');
}

Solution

  • Ok here is the solution not needing any custom written queries but using the appropriate methods available in the WooCommerce Booking plugin.

    add_action('woocommerce_order_status_pool-payment-rec', 'auto_change_booking_status_to_paid', 20, 2 );
    
    function auto_change_booking_status_to_paid( $order_id, $order ) {
    
        if( $order->get_status() === 'pool-payment-rec' ) {
            foreach( $order->get_items() as $item_id => $item ) {
                $product = wc_get_product($item['product_id']);
                if( $product->get_type() === 'booking' ) {
                    $booking_ids = WC_Booking_Data_Store::get_booking_ids_from_order_item_id( $item_id );
    
                    foreach( $booking_ids as $booking_id ) {
                        $booking = new WC_Booking($booking_id);
    
                        if( $booking->get_status() != 'paid' )
                            $booking->update_status( 'paid', 'order_note' );
                    }
    
                }
            }
        }
    }