Show Out of stock products at the end in Woocommer

2019-03-27 23:51发布

Is it possible to show out of stock products at the end of a category or page in wordpress?

So the customer first see the products that are available and after that the products that are out of stock.

6条回答
时光不老,我们不散
2楼-- · 2019-03-28 00:35

This code work for me:

add_action( 'pre_get_posts', function( $query ) {
if ( $query->is_main_query() && is_woocommerce() && ( is_shop() || is_product_category() || is_product_tag() ) ) {
    if( $query->get( 'orderby' ) == 'menu_order title' ) {  // only change default sorting
        $query->set( 'orderby', 'meta_value' );
        $query->set( 'order', 'ASC' );
        $query->set( 'meta_key', '_stock_status' );
    }
}

});

查看更多
一纸荒年 Trace。
3楼-- · 2019-03-28 00:37

Access the global configuration options for inventory management in WooCommerce, look to the left of your WordPress admin and click on WooCommerce, then on Settings, then click on the Inventory tab.

You will find this "Out of Stock Visibility"

Out of Stock Visibility - This checkbox will allow you to determine if you want to hide out of inventory items within the WooCommerce catalog.

http://www.inmotionhosting.com/support/website/woocommerce/managing-inventory-in-woocommerce

For making them appear at the end of the category you could use pre_get_posts to order based on the stock, but then you'll lose your other sorting.

查看更多
神经病院院长
4楼-- · 2019-03-28 00:44

This is the best solution:

add_action( 'pre_get_posts', function ( $q ) {
if (   !is_admin()                 // Target only front end 
     && $q->is_main_query()        // Only target the main query
     && $q->is_post_type_archive() // Change to suite your needs
) {
    $q->set( 'meta_key', '_stock_status' );
    $q->set( 'orderby',  'meta_value'    );
    $q->set( 'order',    'ASC'           );
}

}, PHP_INT_MAX );

查看更多
孤傲高冷的网名
5楼-- · 2019-03-28 00:46

This is the same as Viktor & Bogdan's answer, but without the extra Class code.

It uses the post_clause filter to modify the product query. We JOIN the wp_postmeta table to the query and prepend an orderby _stock_status clause to the existing query. This way any other orderby clauses remain in the query as well.

add_filter('posts_clauses', 'order_by_stock_status');
function order_by_stock_status($posts_clauses) {
    global $wpdb;
    // only change query on WooCommerce loops
    if (is_woocommerce() && (is_shop() || is_product_category() || is_product_tag() || is_product_taxonomy())) {
        $posts_clauses['join'] .= " INNER JOIN $wpdb->postmeta istockstatus ON ($wpdb->posts.ID = istockstatus.post_id) ";
        $posts_clauses['orderby'] = " istockstatus.meta_value ASC, " . $posts_clauses['orderby'];
        $posts_clauses['where'] = " AND istockstatus.meta_key = '_stock_status' AND istockstatus.meta_value <> '' " . $posts_clauses['where'];
    }
    return $posts_clauses;
}

You could change istockstatus.meta_value ASC to istockstatus.meta_value DESC if you for some reason wanted the Out Of Stock items first.

Tested on WP: 4.8; WC 3.0.8

查看更多
Melony?
6楼-- · 2019-03-28 00:47

Here is a snippet for rearranging products (in stock come first):

<?php

/**
 * Order product collections by stock status, instock products first.
 */
class iWC_Orderby_Stock_Status
{

    public function __construct()
    {
        // Check if WooCommerce is active
        if (in_array('woocommerce/woocommerce.php', apply_filters('active_plugins', get_option('active_plugins')))) {
            add_filter('posts_clauses', array($this, 'order_by_stock_status'), 2000);
        }
    }

    public function order_by_stock_status($posts_clauses)
    {
        global $wpdb;
        // only change query on WooCommerce loops
        if (is_woocommerce() && (is_shop() || is_product_category() || is_product_tag())) {
            $posts_clauses['join'] .= " INNER JOIN $wpdb->postmeta istockstatus ON ($wpdb->posts.ID = istockstatus.post_id) ";
            $posts_clauses['orderby'] = " istockstatus.meta_value ASC, " . $posts_clauses['orderby'];
            $posts_clauses['where'] = " AND istockstatus.meta_key = '_stock_status' AND istockstatus.meta_value <> '' " . $posts_clauses['where'];
        }
        return $posts_clauses;
    }
}

new iWC_Orderby_Stock_Status;

?>

https://www.snip2code.com/Snippet/114858/WooCommerce-Products-Order-by-Stock-Stat

查看更多
爷、活的狠高调
7楼-- · 2019-03-28 00:54

Try this code (put in functions.php of your theme):

class iWC_Orderby_Stock_Status {
public function __construct() {
    if (in_array('woocommerce/woocommerce.php', apply_filters('active_plugins', get_option('active_plugins')))) {
        add_filter('posts_clauses', array($this, 'order_by_stock_status'), 2000);
    }
}
public function order_by_stock_status($posts_clauses) {
    global $wpdb;   
    if (is_woocommerce() && (is_shop() || is_product_category() || is_product_tag())) {
        $posts_clauses['join'] .= " INNER JOIN $wpdb->postmeta istockstatus ON ($wpdb->posts.ID = istockstatus.post_id) ";
        $posts_clauses['orderby'] = " istockstatus.meta_value ASC, " . $posts_clauses['orderby'];
        $posts_clauses['where'] = " AND istockstatus.meta_key = '_stock_status' AND istockstatus.meta_value <> '' " . $posts_clauses['where'];
    }
    return $posts_clauses;
    }
}
new iWC_Orderby_Stock_Status;

Taken here.

For the last versions of WooCommerce see answer below: https://stackoverflow.com/a/44597448/3925099

查看更多
登录 后发表回答