Updating product stock programmatically in Woocommerce 3 Updating product stock programmatically in Woocommerce 3 wordpress wordpress

Updating product stock programmatically in Woocommerce 3


Update 2

Since woocommerce 3 "outofstock" product status is saved in 2 locations:

  1. As post meta data for _stock_status meta key (just as before).
  2. As a post term name outofstock remaining to product_visibility custom taxonomy

That means that you missed just a step (the step 3):

$out_of_stock_staus = 'outofstock';// 1. Updating the stock quantityupdate_post_meta($product_id, '_stock', 0);// 2. Updating the stock quantityupdate_post_meta( $product_id, '_stock_status', wc_clean( $out_of_stock_staus ) );// 3. Updating post term relationshipwp_set_post_terms( $product_id, 'outofstock', 'product_visibility', true );// And finally (optionally if needed)wc_delete_product_transients( $product_id ); // Clear/refresh the variation cache

It hope that it will work with your cron job.


Original answer

Your code is a bit outdated since woocommerce 3 and there is no specifically a stock status setting for product variations...

There is a dedicated function in woocommerce to get the product Id from the sku that you could use:

wc_get_product_id_by_sku( $product_sku );

For the parent variable product, you should not need to enabled stock management as this is done in each of its product variations (so at the product variation level).

Since woocommerce 3, the "outofstock" stock status is also managed thought a custom taxonomy product_visibility which term name is outofstock. So updating post meta is not enough.

Also is better to use the new CRUD setters and getters methods introduced with woocommerce 3.

So try the following code instead:

// get the product ID from the SKU$product_id = $wpdb->get_var( $wpdb->prepare( "SELECT post_id FROM $wpdb->postmeta WHERE meta_key='_sku' AND meta_value='%s' LIMIT 1", $sku ) );// Get an instance of the WC_Product object$product = new WC_Product( $product_id );// Get product stock quantity and stock status$stock_quantity = $product->get_stock_quantity();$stock_status   = $product->get_stock_status();// Display stock quantity and statusecho '<p>Product Stock quantity: ' . $stock_quantity . '</br>    Product Stock status: ' . $stock_status . '</p></br>';// Set product stock quantity (zero) and stock status (out of stock)$product->set_stock_quantity();$product->set_stock_status('outofstock');// Save the data and refresh caches$product->save();

Tested and works in a normal context (but apparently not with a cron job)


LoicTheAztecs update works fine(thank you)

But I was thinking: Why isn't there a WC-standard function for this?

So I found the:

wc_update_product_stock function

 wc_update_product_stock($product, $stock_quantity=null, $operation='set', $updating = false)
  • @param int|WC_Product | $product |Product ID or product instance.
  • @param int|null | $stock_quantity Stock quantity.
  • @param string | $operation Type of opertion, allows 'set', 'increase' and 'decrease'.
  • @param bool | $updating | If true, the product object won't be saved here as it will be updated later.
  • @return bool|int|null