How to Hide Out of Stock Products
In this step-by-step guide, I would like to show you how you can hide out of stock products and variations on your WooCommerce store (or show them, if they are hidden at this moment).
By default, when a product is out of stock it is still going to be displayed on your shop and archive pages. Instead of the “Add to cart” button, there is going to be displayed the “Read more” button.

By the way, there is also another option – we can display products in stock always first.
The methods I am going to show you below will work great if you also decide to hide out of stock variations on your WooCommerce store. However, for product variations, you may consider making them displayed half-transparent or in a grey color.
How to Hide Out of Stock Products in WooCommerce Settings
If you’re already getting ready to use some code snippets – no need to worry about that. In most cases you don’t even need them, all you need to do is to go to the WooCommerce settings, then to the “Products” tab, and then to the “Inventory” tab.
“Hide out of stock items from the catalog” – is the checkbox you need to check.

The products will still be available by their direct links, which is great because products could be bookmarked in the browsers, but they won’t be displayed on the following pages:
- the shop page,
- product category and tag archive pages,
- search results,
- related products, upsells, and cross-sell sections.
Hide Out of Stock Products Programmatically
First of all, let’s get a clear picture of how the stock settings are stored in each specific product
Basically, it is just a custom field with the key _stock_status which can have the following values:
instock,outofstock,onbackorder.
It means that we have two ways how we can hide out of stock products and variations programmatically:
- We can use the
pre_option_{$option}hook to modify the value of the setting we discussed before right after WooCommerce gets its value from the database. - Or we can modify the Meta_Query value of a product query using the
pre_get_postshook.
I also saw an example out there, where a guy suggested passing the meta_query parameter to the woocommerce_output_related_products_args filter hook. I want to clarify one moment – this filter hook supports only posts_per_page, columns, orderby and order parameters.
So if you need to hide your out of stock products from some specific places on the website and somehow the first method is not what you need, I recommend you to check the pre_option_{option name} filter hook.
/**
* WooCommerce: Hide Out of Stock Products On Specific Pages
*/
add_filter( 'pre_option_woocommerce_hide_out_of_stock_items', function( $option ) {
if( is_admin() ) { // admin dashboard
return $option;
}
if( is_search() ) {
return $option;
}
$option = 'yes';
return $option;
} );As you can see in the above code, we excluded the search results page with the help of the is_search() function. It means that you can also use other conditional tags.
You can also do that by modifying the Meta_Query value in the pre_get_posts action hook, but please be careful, because this code may also be applied to your blog posts or anything else on the website.
/**
* WooCommerce: Hide Out of Stock Products By Modifying Meta_Query
*/
add_action( 'pre_get_posts', function( $query ){
// Run Only on the Shop Page
if( is_shop() ) {
$query->set(
'meta_query',
array(
array(
'key' => '_stock_status',
'value' => 'instock',
),
)
);
// OR
//$query->set( 'meta_key', '_stock_status' );
//$query->set( 'meta_value', 'instock' );
}
} );Last but not least, let’s take a look at the “Related products” example. This method may seem a little bit tricky, but it works perfectly.
/**
* WooCommerce: Hide Out of Stock Related Products
*/
function rudr_return_yes( $option ){
return 'yes';
}
add_action( 'woocommerce_before_template_part', function( $template_name ) {
if( 'single-product/related.php' !== $template_name ) {
return;
}
add_filter( 'pre_option_woocommerce_hide_out_of_stock_items', 'rudr_return_yes' );
} );
add_action( 'woocommerce_after_template_part', function( $template_name ) {
if( 'single-product/related.php' !== $template_name ) {
return;
}
remove_filter( 'pre_option_woocommerce_hide_out_of_stock_items', 'rudr_return_yes' );
} );A couple of notes:
- On line 1 you can see the function that always returns “yes” no matter which option value is set in WooCommerce settings.
- We filter the option on the line
12, but we create a filter only before our specific WooCommerce template part is included, that’s why it is inside an actionwoocommerce_before_template_partand there is also a condition on the line9. - Once the template is included, we don’t want this option to be filtered for the rest of the page, so we remove the filter on the line
19and do it inside the action hookwoocommerce_after_template_part. - If you want to do the same for upsells, just replace the template name to
single-product/up-sells.php, for cross-sells – tocart/cross-sells.php.
Misha Rudrastyh
Hey guys and welcome to my website. For more than 15 years I've been doing my best to share with you some superb WordPress guides and tips for free.
Need some developer help? Contact me
I added the code to my functions.php to disable the ‘out of stock’ items in the related products section, but now it’s not showing any related products anymore. Also no items which are still for sale.
Do you know what could be the problem? Thanks in advance!
hi Misha,
nice code, i dont think peeps are reading so were and they have not relised that theres two functions displaying in first code functions section, prehaps define clearer for others.
You’re the best bro. i was looking for a solution like that, thank you so much!!
Thanks, great job and explanation