Objective: add product to cart despite unselected variations, i.e. remove/disable the mandatory nature of variation fields.
Issue: WooCommerce’s absolute requirement for all variations to be selected before adding to cart.
Tried: filtering out/removing/disabling unselected variations before adding to cart using various hooks; woocommerce_before_calculate_totals
, woocommerce_add_to_cart
, woocommerce_add_cart_item
, woocommerce_add_to_cart_validation
I understand that this is how WooCommerce works and the reasons why it works this way – despite this I still require a work-around.
How do I get around WooCommerce’s "all variations selected" requirement so that I may still add a product to the cart even if not all variations are selected?
2
Answers
1 – You could use "variation" attributes, and "not-variation" attributes. UPDATED AFTER TESTS
For the attribute that will handle your product price:
create a variable product
create real Woocommerce product attributes (real taxonomy and terms) (it won’t work with "created on product page" attributes, as it’ll not create real taxonomy and terms)
Here I created 3 attributes with some terms
On your variable product, I choose all of my 3 attributes. But specified to only use Color and Size for variations (so Color and Variations will handle my prices variations), not the attribute "optional" (that will be an optional option)
Then, generate your variations. You can see here that I only have variations for a combination of Color and Size, nothing about the "Optional" attribute yet
Also, select the "default values" for your variation attributes. So on the frontend, the attribute select HTML input will have a pre-selected option (user can add to cart directly)
Now we have our variation attributes, with preselected values on the frontend
But we still miss our "optional" attributes
Add the following code to your
function.php
or related (Inspired, updated/refreshed, and adapted from this) (sorry for formatting, snippet also available as gist)This will handle outputting the select input for the optional attribute, saving it to cart and to order. You can adapt it to make it required or not, with a default value or not, edit HTML and placement with different hooks.
Results:
2 – Plugins
You could also check with plugins like Product Add-Ons or Extra Product Options (Product Addons) for WooCommerce.
In addition to real Woocommerce product variations with your attribute handling prices, those plugins could allow you to add optional fields on the product level when adding it to the cart. It can be enough if you don’t need real product variations for those "optional" attributes, but only "optional fields that will be saved to the order line-item product".
3 – with hooks (tweaks)
Now, if you really need to use hooks to handle this issue, and you already have variations for required and optional attributes. So you generated all product variations for all attributes. But in the end, only 1 attribute has a price impact, so many variations have the same price).
You could first try to handle it with "default" attributes values. So by only changing the "required price impacting" attribute, the user always has an existing product variation from the combination of attributes. So it can be added to the cart.
If for some reason, you cannot preselect the default yourself: still create the default attribute term, and hook before add to cart. There, from the POST variables, you could:
The thing is with the variable products: attributes are nothing for the checkout process. When user select options (attributes) on the frontend, he selects a combination of attribute that have or not a corresponding product variation (created by admin, or with woocommerce helper). Woocommerce needs an existing product variation (combination of attributes), that you can see on the product page, to add something to the cart. Those variations are in DB a custom post_type "product_variation" that can be added to the cart and to a order as line-item.
If the combination of attributes doesn’t have a matching product variation: there’s nothing to add to the cart.
You can try