Search the site:

Home Blog How to filter WooCommerce orders by multiple order statuses?

How to filter WooCommerce orders by multiple order statuses?

One of our customers recently asked us this question for their WooCommerce Orders page in admin: Is there a way to select multiple statuses in the order backend?

Although WooCommerce store owners may not need to do this on a regular basis, but this would definitely help some of them.

This post will explains how to show WooCommerce orders with different statuses in one view. In the 2nd half of this post, we will also check how to exclude one or multiple statuses when all orders are being displayed.

The default behaviour of WooCommerce is that you can either view All orders, or orders for any one status. But you cannot view orders of different statuses together, like Pending & Refunded orders. Or you cannot exclude orders of a status in the All view.

WooCommerce Orders in Admin
Default WooCommerce Orders page view

Apart from the default order statuses, I have added a custom order status: Delivered . This has been added using the Custom Order Status plugin & is added to verify that the filtering would also work with custom order statuses along with the default statuses.

Part 1: Filter WooCommerce Orders to show orders of multiple statuses in one view

There are multiple ways to look for a solution for this. It could either be via a plugin, or by adding a multi-select dropdown of order status with a code snippet. Or a crude way, simply add the status you want in the URL.

It’s definitely not the best way, but it works. I may come back later to this post & update it to include a multi-select dropdown of WooCommerce order statuses.

Let’s look at the code first.

/**
 * Handle filters for including additional woocommerce statuses
 *
 * @param array $query_vars Query vars.
 * @return array
 */
function ts_woocommerce_include_order_status( $query_vars ) {
  global $typenow;

  /**
   * Using wc_get_order_types() instead of 'shop_order' as other order types could be added by other plugins
   */
  if ( in_array( $typenow, wc_get_order_types( 'order-meta-boxes' ), true ) ) {
    if ( isset( $_GET['include_status'] ) && '' != $_GET['include_status']
       && isset( $query_vars['post_status'] ) ) {
      $include_status = explode( ',', $_GET['include_status'] );
      $q_post_status[]  = $query_vars['post_status'];
      $query_vars['post_status'] = array_merge( $q_post_status, $include_status );
    }
  }
  return $query_vars;
}
add_filter( 'request', 'ts_woocommerce_include_order_status', 20, 1 );

We are doing a few things in the above snippet.

First, we attach our function to the request filter of WordPress.

Because we want our code to run only for the WooCommerce Orders page, we do that by making sure that the $typenow variable is present in the array returned from wc_get_order_types() function. In this case, $typenow is set to shop_order. That is the post_type of the orders that are created by WooCommerce.

include_status is the GET variable wherein you should pass other order statuses that you wish to be displayed. Multiple order statuses can be passed comma separated. You should first filter the order by any 1 order status that you wish to see. Let’s say you filtered by pending orders.

WooCommerce Orders with Pending status
WooCommerce Orders with Pending status

If you want to see the Refunded orders along with the Pending orders, that isn’t possible. However, if you add the above code snippet in your child theme’s functions.php, and then if you change the URL of the Orders page to the below link in your browser:

<your_store_url>/wp-admin/edit.php?post_status=wc-pending&post_type=shop_order&include_status=wc-refunded

you shall see that the Pending as well as Refunded orders will show up.

WooCommerce orders with status as Pending & Refunded being shown
WooCommerce orders with status as Pending & Refunded being shown

In the include_status parameter, you can also pass multiple order statuses which are comma separated. So if you want to view Pending, Refunded & Delivered orders, you can do so by changing the URL as below:

<your_store_url>/wp-admin/edit.php?post_status=wc-pending&post_type=shop_order&include_status=wc-refunded,wc-delivered

It’s important to note that Delivered is a custom status that I have added in my test WooCommerce install. It’s slug is wc-delivered. The status is added with the Custom Order Status plugin.

When you open the above link, you will see the orders with those 3 statuses:

WooCommerce orders with status as Pending, Refunded & Delivered being shown
WooCommerce orders with status as Pending, Refunded & Delivered being shown

The comma in the URL gets replaced with %2C due to URL encoding.

Part 2: Filter WooCommerce Orders to hide orders of one or more statuses in the All view

By default, you are presented with a view where WooCommerce orders of all statuses are shown on the Orders page.

WooCommerce Orders in Admin

I have created below code snippet that allows you to pass a variable in the URL, exclude_status. In the exclude_status variable, you can pass the slug of the status that you wish to exclude from being displayed on the Orders page in the All view. Here is the code:

/**
 * Handle filters for excluding woocommerce statuses from All orders view
 *
 * @param array $query_vars Query vars.
 * @return array
 */
function ts_woocommerce_exclude_order_status( $query_vars ) {
  global $typenow;

  /**
   * Using wc_get_order_types() instead of 'shop_order' as other order types could be added by other plugins
   */
  if ( in_array( $typenow, wc_get_order_types( 'order-meta-boxes' ), true ) ) {
    if ( isset( $_GET['exclude_status'] ) && '' != $_GET['exclude_status']
       && isset( $query_vars['post_status'] ) ) {
      $exclude_status = explode( ',', $_GET['exclude_status'] );
      foreach ( $exclude_status as $key => $value ) {
        if ( ( $key = array_search( $value, $query_vars['post_status'] ) ) !== false) {
          unset( $query_vars['post_status'][$key] );
        }
      }
    }
  }
  return $query_vars;
}
add_filter( 'request', 'ts_woocommerce_exclude_order_status', 20, 1 );

When the above code is added in your child theme’s functions.php file, and then if you change the URL of your WooCommerce Orders page to the one below:

<your_store_url>/wp-admin/edit.php?post_type=shop_order&exclude_status=wc-pending

Then the orders with Pending status will not be displayed in the default view of All orders:

Excludes Pending orders from being displayed from all orders view
Excludes Pending orders from being displayed from all orders view

You can also specify multiple order statuses to exclude. They need to be separated by comma. Expanding on the above example, if you want to hide Pending & Delivered orders from the All view, then you can change your Orders page URL to:

<your_store_url>/woocommerce/wp-admin/edit.php?post_type=shop_order&exclude_status=wc-pending,wc-delivered

The Orders page will no longer show Pending & Delivered orders on the All view:

Excludes Pending & Delivered orders from being displayed from all orders view
Excludes Pending & Delivered orders from being displayed from all orders view

Here is a reference of the default WooCommerce order statuses & their respective slugs.

  • Pending payment – wc-pending
  • Failed – wc-failed
  • Processing – wc-processing
  • Completed – wc-completed
  • On-Hold – wc-on-hold
  • Cancelled – wc-cancelled
  • Refunded – wc-refunded

Adding the order statuses in the URL directly isn’t the best approach. But the idea of this post is to show how the objective can be achieved.

Have you tried any other approach for filtering orders by order statuses in WooCommerce? I would love to know them.

Browse more in: Code Snippets, WooCommerce How Tos, WooCommerce Tutorials

1
Leave a Reply

avatar
1 Comment threads
0 Thread replies
2 Followers
 
Most reacted comment
Hottest comment thread
1 Comment authors
Joe Recent comment authors

This site uses Akismet to reduce spam. Learn how your comment data is processed.

  Subscribe  
newest oldest
Notify of
Joe
Guest
Joe

This does not work

from purchased

Subscribe for more offers