Sorting order items by SKU in Woocommerce

后端 未结 2 767
旧时难觅i
旧时难觅i 2020-12-12 03:02

I am trying to order the products by sku within an order in an email in Woocommerce.

I have not had any luck with the following code

相关标签:
2条回答
  • 2020-12-12 03:41

    Updated On July 2020

    Here is the way to do it:

    add_filter( 'woocommerce_order_get_items', 'filter_order_get_items_by_sku', 10, 3 );
    function filter_order_get_items_by_sku( $items, $order, $types ) {
        if( count($items) > 1 ) {
            $item_skus = $sorted_items = array();
    
            // Loop through order line items
            foreach( $items as $items_id => $item ){
                // Check items type: for versions before Woocommerce 3.3
                if( $item->is_type('line_item') && method_exists( $item, 'get_product' ) ){
                    $product = $item->get_product(); // Get the product Object
                    if( is_a( $product, 'WC_Product' ) ) {
                        $item_skus[$product->get_sku()] = $items_id;
                    }
                }
            }
    
            // Only for line items when our sku array is not empty
            if( ! empty($item_skus) ) {
                // Sorting in ASC order based on SKUs;
                ksort($item_skus); // or use krsort() for DESC order
    
                // Loop through sorted $item_skus array
                foreach( $item_skus as $sku => $item_id ){
                    // Set items in the correct order
                    $sorted_items[$item_id] = $items[$item_id];
                }
                $items = $sorted_items;
            }
        }
        return $items;
    }
    

    Code goes in function.php file of your active child theme (or active theme). Tested and works.

    This will sort items by sku order ASC on backend and frontend orders and in email notifications


    Also sorting items once the order is placed before data is saved to the database, could be a better way to do it.

    0 讨论(0)
  • 2020-12-12 03:41

    In addition to @LoicTheAztec I've added the following check in the code:

    if ($product instanceof WC_Product) {
                        $item_skus[$product->get_sku()] = $items_id;
                    }
    

    This prevents an error on the front-end customer orders page.

    add_filter( 'woocommerce_order_get_items', 'filter_order_get_items_by_sku', 10, 3 );
    function filter_order_get_items_by_sku( $items, $order, $types ) {
        if( count($items) > 1 ) {
            $item_skus = $sorted_items = array();
    
            // Loop through order line items
            foreach( $items as $items_id => $item ){
                // Check items type: for versions before Woocommerce 3.3
                if( $item->is_type('line_item') ){
                    $product = $item->get_product(); // Get the product Object
                    
                    if ($product instanceof WC_Product) {
                        $item_skus[$product->get_sku()] = $items_id;
                    }
                }
            }
    
            // Only for line items when our sku array is not empty
            if( ! empty($item_skus) ) {
                // Sorting in ASC order based on SKUs;
                ksort($item_skus); // or use krsort() for DESC order
    
                // Loop through sorted $item_skus array
                foreach( $item_skus as $sku => $item_id ){
                    // Set items in the correct order
                    $sorted_items[$item_id] = $items[$item_id];
                }
                $items = $sorted_items;
            }
        }
        return $items;
    }
    
    0 讨论(0)
提交回复
热议问题